Skip to content
Merged
Show file tree
Hide file tree
Changes from all 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
3 changes: 2 additions & 1 deletion docs/docusaurus.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ const config = {
},
routeBasePath: "/",
include: ["**/*.{md,mdx}"],
exclude: !process.env.PROTOCOL_SPECS ? ['protocol-specs/**'] : [],
exclude: !process.env.PROTOCOL_SPECS ? ["protocol-specs/**"] : [],

remarkPlugins: [math],
rehypePlugins: [
Expand All @@ -76,6 +76,7 @@ const config = {
},
],
],
includeCurrentVersion: false,
versions: (() => {
const versionObject = {};
if (process.env.ENV === "dev") {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"label": "Uniswap Bridge",
"position": 7,
"label": "Concepts",
"position": 1,
"collapsible": true,
"collapsed": true
}
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ However if one wants to implement authorization logic containing signatures (e.g

This is a snippet of our Schnorr Account contract implementation, which uses Schnorr signatures for authentication:

```rust title="is_valid_impl" showLineNumbers
```rust title="is_valid_impl" showLineNumbers
// Load public key from storage
let storage = Storage::init(context);
let public_key = storage.signing_public_key.get_note();
Expand All @@ -102,7 +102,7 @@ let pub_key = std::embedded_curve_ops::EmbeddedCurvePoint {
// Verify signature of the payload bytes
schnorr::verify_signature(pub_key, signature, outer_hash.to_be_bytes::<32>())
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L65-L86" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L65-L86</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L65-L86" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L65-L86</a></sub></sup>


### Storing signing keys
Expand All @@ -117,10 +117,10 @@ Storing the signing public key in a private note makes it accessible from the `e

Using an immutable private note removes the need to nullify the note on every read. This generates no nullifiers or new commitments per transaction. However, it does not allow the user to rotate their key.

```rust title="public_key" showLineNumbers
```rust title="public_key" showLineNumbers
signing_public_key: PrivateImmutable<PublicKeyNote, Context>,
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L28-L30" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L28-L30</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L28-L30" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/account/schnorr_account_contract/src/main.nr#L28-L30</a></sub></sup>


:::note
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ We also need to create a point for the owner of the FPC (whom we call Bob) to re
So in the contract we compute $\text{rand}_b := h(\text{rand}_a, \text{msg sender})$.

:::warning
We need to use different randomness for Bob's note here to avoid potential privacy leak (see [description](https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/app/token_contract/src/main.nr#L491) of `setup_refund` function)
We need to use different randomness for Bob's note here to avoid potential privacy leak (see [description](https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/app/token_contract/src/main.nr#L491) of `setup_refund` function)
:::

$$
Expand Down Expand Up @@ -144,7 +144,7 @@ We can see the complete implementation of creating and completing partial notes

#### `fee_entrypoint_private`

```rust title="fee_entrypoint_private" showLineNumbers
```rust title="fee_entrypoint_private" showLineNumbers
#[private]
fn fee_entrypoint_private(max_fee: u128, nonce: Field) {
let accepted_asset = storage.config.read().accepted_asset;
Expand All @@ -170,15 +170,15 @@ fn fee_entrypoint_private(max_fee: u128, nonce: Field) {
context.set_as_fee_payer();
}
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L78-L103" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L78-L103</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L78-L103" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L78-L103</a></sub></sup>


The `fee_entrypoint_private` function sets the `complete_refund` function to be called at the end of the public function execution (`set_public_teardown_function`).
This ensures that the refund partial note will be completed for the user.

#### `complete_refund`

```rust title="complete_refund" showLineNumbers
```rust title="complete_refund" showLineNumbers
#[public]
#[internal]
fn _complete_refund(
Expand All @@ -201,7 +201,7 @@ fn _complete_refund(
);
}
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L107-L129" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L107-L129</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L107-L129" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L107-L129</a></sub></sup>


## Note discovery
Expand Down
46 changes: 23 additions & 23 deletions docs/versioned_docs/version-Latest/aztec/concepts/call_types.md
Original file line number Diff line number Diff line change
Expand Up @@ -102,10 +102,10 @@ Contract functions marked with `#[private]` can only be called privately, and as

Private functions from other contracts can be called either regularly or statically by using the `.call()` and `.static_call` functions. They will also be 'executed' (i.e. proved) in the user's device, and `static_call` will fail if any state changes are attempted (like the EVM's `STATICCALL`).

```rust title="private_call" showLineNumbers
```rust title="private_call" showLineNumbers
let _ = Token::at(stable_coin).burn_private(from, amount, nonce).call(&mut context);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L254-L256" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L254-L256</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L254-L256" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L254-L256</a></sub></sup>


Unlike the EVM however, private execution doesn't revert in the traditional way: in case of error (e.g. a failed assertion, a state changing operation in a static context, etc.) the proof generation simply fails and no transaction request is generated, spending no network gas or user funds.
Expand All @@ -116,38 +116,38 @@ Since public execution can only be performed by the sequencer, public functions

Since the public call is made asynchronously, any return values or side effects are not available during private execution. If the public function fails once executed, the entire transaction is reverted including state changes caused by the private part, such as new notes or nullifiers. Note that this does result in gas being spent, like in the case of the EVM.

```rust title="enqueue_public" showLineNumbers
```rust title="enqueue_public" showLineNumbers
Lending::at(context.this_address())
._deposit(AztecAddress::from_field(on_behalf_of), amount, collateral_asset)
.enqueue(&mut context);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L119-L123" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L119-L123</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L119-L123" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/lending_contract/src/main.nr#L119-L123</a></sub></sup>


It is also possible to create public functions that can _only_ be invoked by privately enqueueing a call from the same contract, which can be very useful to update public state after private execution (e.g. update a token's supply after privately minting). This is achieved by annotating functions with `#[internal]`.

A common pattern is to enqueue public calls to check some validity condition on public state, e.g. that a deadline has not expired or that some public value is set.

```rust title="enqueueing" showLineNumbers
```rust title="enqueueing" showLineNumbers
Router::at(ROUTER_ADDRESS).check_block_number(operation, value).call(context);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L17-L19" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L17-L19</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L17-L19" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L17-L19</a></sub></sup>


Note that this reveals what public function is being called on what contract, and perhaps more importantly which contract enqueued the call during private execution.
For this reason we've created a canonical router contract which implements some of the checks commonly performed: this conceals the calling contract, as the `context.msg_sender()` in the public function will be the router itself (since it is the router that enqueues the public call).

An example of how a deadline can be checked using the router contract follows:

```rust title="call-check-deadline" showLineNumbers
```rust title="call-check-deadline" showLineNumbers
privately_check_timestamp(Comparator.LT, config.deadline, &mut context);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/app/crowdfunding_contract/src/main.nr#L68-L70" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/crowdfunding_contract/src/main.nr#L68-L70</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/app/crowdfunding_contract/src/main.nr#L68-L70" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/crowdfunding_contract/src/main.nr#L68-L70</a></sub></sup>


`privately_check_timestamp` and `privately_check_block_number` are helper functions around the call to the router contract:

```rust title="helper_router_functions" showLineNumbers
```rust title="helper_router_functions" showLineNumbers
/// Asserts that the current timestamp in the enqueued public call enqueued by `check_timestamp` satisfies
/// the `operation` with respect to the `value. Preserves privacy by performing the check via the router contract.
/// This conceals an address of the calling contract by setting `context.msg_sender` to the router contract address.
Expand All @@ -162,12 +162,12 @@ pub fn privately_check_block_number(operation: u8, value: Field, context: &mut P
Router::at(ROUTER_ADDRESS).check_block_number(operation, value).call(context);
}
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L5-L21" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L5-L21</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L5-L21" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/utils.nr#L5-L21</a></sub></sup>


This is what the implementation of the check timestamp functionality looks like:

```rust title="check_timestamp" showLineNumbers
```rust title="check_timestamp" showLineNumbers
/// Asserts that the current timestamp in the enqueued public call satisfies the `operation` with respect
/// to the `value.
#[private]
Expand All @@ -186,7 +186,7 @@ fn _check_timestamp(operation: u8, value: u64) {
assert(compare(lhs_field, operation, rhs_field), "Timestamp mismatch.");
}
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/protocol/router_contract/src/main.nr#L13-L31" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/main.nr#L13-L31</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/protocol/router_contract/src/main.nr#L13-L31" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/protocol/router_contract/src/main.nr#L13-L31</a></sub></sup>


:::note
Expand All @@ -195,7 +195,7 @@ To add it as a dependency point to the aztec-packages repository instead:

```toml
[dependencies]
aztec = { git = "https://github.com/AztecProtocol/aztec-packages/", tag = "v0.87.3", directory = "noir-projects/noir-contracts/contracts/protocol/router_contract/src" }
aztec = { git = "https://github.com/AztecProtocol/aztec-packages/", tag = "v0.87.4", directory = "noir-projects/noir-contracts/contracts/protocol/router_contract/src" }
```

:::
Expand All @@ -212,12 +212,12 @@ Since private calls are always run in a user's device, it is not possible to per

Public functions in other contracts can be called both regularly and statically, just like on the EVM.

```rust title="public_call" showLineNumbers
```rust title="public_call" showLineNumbers
Token::at(config.accepted_asset)
.transfer_in_public(context.msg_sender(), context.this_address(), max_fee, nonce)
.enqueue(&mut context);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L156-L160" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L156-L160</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L156-L160" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/fees/fpc_contract/src/main.nr#L156-L160</a></sub></sup>


:::note
Expand All @@ -236,21 +236,21 @@ There are three different ways to execute an Aztec contract function using the `

This is used to get a result out of an execution, either private or public. It creates no transaction and spends no gas. The mental model is fairly close to that of [`eth_call`](#eth_call), in that it can be used to call any type of function, simulate its execution and get a result out of it. `simulate` is also the only way to run [utility functions](#utility).

```rust title="public_getter" showLineNumbers
```rust title="public_getter" showLineNumbers
#[public]
#[view]
fn get_authorized() -> AztecAddress {
storage.authorized.get_current_value()
}
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/noir-projects/noir-contracts/contracts/app/auth_contract/src/main.nr#L42-L50" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/auth_contract/src/main.nr#L42-L50</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/noir-projects/noir-contracts/contracts/app/auth_contract/src/main.nr#L42-L50" target="_blank" rel="noopener noreferrer">Source code: noir-projects/noir-contracts/contracts/app/auth_contract/src/main.nr#L42-L50</a></sub></sup>


```typescript title="simulate_function" showLineNumbers
```typescript title="simulate_function" showLineNumbers
const balance = await contract.methods.balance_of_public(newWallet.getAddress()).simulate();
expect(balance).toEqual(1n);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/yarn-project/end-to-end/src/composed/docs_examples.test.ts#L54-L57" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/composed/docs_examples.test.ts#L54-L57</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/yarn-project/end-to-end/src/composed/docs_examples.test.ts#L54-L57" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/composed/docs_examples.test.ts#L54-L57</a></sub></sup>


:::warning
Expand All @@ -261,19 +261,19 @@ No correctness is guaranteed on the result of `simulate`! Correct execution is e

This creates and returns a transaction request, which includes proof of correct private execution and side-effects. The request is not broadcast however, and no gas is spent. It is typically used in testing contexts to inspect transaction parameters or to check for execution failure.

```typescript title="local-tx-fails" showLineNumbers
```typescript title="local-tx-fails" showLineNumbers
const call = token.methods.transfer(recipient.getAddress(), 200n);
await expect(call.simulate()).rejects.toThrow(/Balance too low/);
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/yarn-project/end-to-end/src/guides/dapp_testing.test.ts#L123-L126" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/guides/dapp_testing.test.ts#L123-L126</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/yarn-project/end-to-end/src/guides/dapp_testing.test.ts#L123-L126" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/guides/dapp_testing.test.ts#L123-L126</a></sub></sup>


#### `send`

This is the same as [`prove`](#prove) except it also broadcasts the transaction and returns a receipt. This is how transactions are sent, getting them to be included in blocks and spending gas. It is similar to [`eth_sendTransaction`](#eth_sendtransaction), except it also performs some work on the user's device, namely the production of the proof for the private part of the transaction.

```typescript title="send_tx" showLineNumbers
```typescript title="send_tx" showLineNumbers
await contract.methods.buy_pack(seed).send().wait();
```
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.3/yarn-project/end-to-end/src/e2e_card_game.test.ts#L129-L131" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/e2e_card_game.test.ts#L129-L131</a></sub></sup>
> <sup><sub><a href="https://github.com/AztecProtocol/aztec-packages/blob/v0.87.4/yarn-project/end-to-end/src/e2e_card_game.test.ts#L129-L131" target="_blank" rel="noopener noreferrer">Source code: yarn-project/end-to-end/src/e2e_card_game.test.ts#L129-L131</a></sub></sup>

Loading