Skip to content

Commit

Permalink
Release 2.1.0. (#331)
Browse files Browse the repository at this point in the history
* Modify message verification inside ft_transfer_call for external receiver_id (#326)
* Fix call to ft_resolve_transfer; extend tests (#330)
* Fix(precompile): correct ripemd160 word cost (#329)

Co-authored-by: Evgeny Ukhanov <evgeny@aurora.dev>
Co-authored-by: Joshua J. Bouw <joshua@aurora.dev>
Co-authored-by: Michael Birch <michael@aurora.dev>
  • Loading branch information
4 people authored Nov 5, 2021
1 parent c5454c1 commit c4f4edb
Show file tree
Hide file tree
Showing 19 changed files with 890 additions and 59 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ etc/eth-contracts/res/

# Other
etc/state-migration-test/target/
etc/ft-receiver/target/

node_modules/*
cache
11 changes: 10 additions & 1 deletion CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,13 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [Unreleased]

## [2.1.0] - 2021-11-04

### Fixed

- Bug in `ft_transfer_call` and `ft_resolve_transfer` by [@birchmd] and [@mrLSD]. ([#326](https://github.com/aurora-is-near/aurora-engine/pull/326) [#330](https://github.com/aurora-is-near/aurora-engine/pull/330))
- Incorrect gas cost on ripemd precompile by [@joshuajbouw]. ([#329](https://github.com/aurora-is-near/aurora-engine/pull/329))

## [2.0.2] - 2021-11-01

### Added
Expand Down Expand Up @@ -132,7 +139,8 @@ struct SubmitResult {

## [1.0.0] - 2021-05-12

[Unreleased]: https://github.com/aurora-is-near/aurora-engine/compare/2.0.0...master
[Unreleased]: https://github.com/aurora-is-near/aurora-engine/compare/2.1.0...master
[2.1.0]: https://github.com/aurora-is-near/aurora-engine/compare/2.0.2...2.1.0
[2.0.2]: https://github.com/aurora-is-near/aurora-engine/compare/2.0.1...2.0.2
[2.0.1]: https://github.com/aurora-is-near/aurora-engine/compare/2.0.0...2.0.1
[2.0.0]: https://github.com/aurora-is-near/aurora-engine/compare/1.7.0...2.0.0
Expand All @@ -152,6 +160,7 @@ struct SubmitResult {
[1.1.0]: https://github.com/aurora-is-near/aurora-engine/compare/1.0.0...1.1.0
[1.0.0]: https://github.com/aurora-is-near/aurora-engine/tree/1.0.0

[@mrLSD]: https://github.com/mrLSD
[@birchmd]: https://github.com/birchmd
[@joshuajbouw]: https://github.com/joshuajbouw
[@sept-en]: https://github.com/sept-en
2 changes: 1 addition & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -36,5 +36,6 @@ members = [
"engine-tests"
]
exclude = [
"etc/state-migration-test"
"etc/state-migration-test",
"etc/ft-receiver",
]
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,10 @@ documentation.

Network | Contract ID | Chain ID | Version
------- | ------------------- | ---------- | ------
Mainnet | [`aurora`][Mainnet] | 1313161554 | 2.0.2
Testnet | [`aurora`][Testnet] | 1313161555 | 2.0.2
Betanet | [`aurora`][Betanet] | 1313161556 | 2.0.2
Local | `aurora.test.near` | 1313161556 | 2.0.2
Mainnet | [`aurora`][Mainnet] | 1313161554 | 2.1.0
Testnet | [`aurora`][Testnet] | 1313161555 | 2.1.0
Betanet | [`aurora`][Betanet] | 1313161556 | 2.1.0
Local | `aurora.test.near` | 1313161556 | 2.1.0

[Mainnet]: https://explorer.near.org/accounts/aurora
[Testnet]: https://explorer.testnet.near.org/accounts/aurora
Expand Down
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
2.0.2
2.1.0
2 changes: 1 addition & 1 deletion engine-precompiles/src/hash.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ mod costs {

pub(super) const RIPEMD160_BASE: u64 = 600;

pub(super) const RIPEMD160_PER_WORD: u64 = 12;
pub(super) const RIPEMD160_PER_WORD: u64 = 120;
}

mod consts {
Expand Down
1 change: 1 addition & 0 deletions engine-tests/src/test_utils/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ pub(crate) const SUBMIT: &str = "submit";
pub(crate) mod erc20;
pub(crate) mod exit_precompile;
pub(crate) mod one_inch;
pub(crate) mod rust;
pub(crate) mod self_destruct;
pub(crate) mod solidity;
pub(crate) mod standard_precompiles;
Expand Down
14 changes: 14 additions & 0 deletions engine-tests/src/test_utils/rust.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
use std::path::Path;
use std::process::Command;

pub fn compile<P: AsRef<Path>>(source_path: P) {
let output = Command::new("cargo")
.current_dir(source_path)
.args(&["build", "--target", "wasm32-unknown-unknown", "--release"])
.output()
.unwrap();

if !output.status.success() {
panic!("{}", String::from_utf8(output.stderr).unwrap());
}
}
140 changes: 140 additions & 0 deletions engine-tests/src/tests/eth_connector.rs
Original file line number Diff line number Diff line change
Expand Up @@ -457,6 +457,138 @@ fn test_ft_transfer_call_eth() {
assert_eq!(balance, transfer_amount);
}

#[test]
fn test_ft_transfer_call_without_message() {
let (master_account, contract) = init(CUSTODIAN_ADDRESS);
let recipient_account = create_user_account(&master_account);
call_deposit_eth_to_near(&contract, CONTRACT_ACC);

let balance = get_eth_on_near_balance(&master_account, DEPOSITED_RECIPIENT, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT - DEPOSITED_FEE);

let balance = get_eth_on_near_balance(&master_account, CONTRACT_ACC, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_FEE);

let res = contract.call(
CONTRACT_ACC.parse().unwrap(),
"register_relayer",
&RegisterRelayerCallArgs {
address: validate_eth_address(CUSTODIAN_ADDRESS),
}
.try_to_vec()
.unwrap(),
DEFAULT_GAS,
0,
);
res.assert_success();

let transfer_amount = 50;
// Send to Aurora contract with wrong message should failed
let res = contract.call(
CONTRACT_ACC.parse().unwrap(),
"ft_transfer_call",
json!({
"receiver_id": CONTRACT_ACC,
"amount": transfer_amount.to_string(),
"msg": "",
})
.to_string()
.as_bytes(),
DEFAULT_GAS,
1,
);
match res.outcome().status {
ExecutionStatus::Failure(_) => {}
_ => panic!("Expected execution failure"),
}

// Assert balances remain unchanged
let balance = get_eth_on_near_balance(&master_account, DEPOSITED_RECIPIENT, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT - DEPOSITED_FEE);
let balance = get_eth_on_near_balance(&master_account, CONTRACT_ACC, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_FEE);

// Sending to random account should not change balances
let transfer_amount = 22;
let res = recipient_account.call(
CONTRACT_ACC.parse().unwrap(),
"ft_transfer_call",
json!({
"receiver_id": "some-test-acc",
"amount": transfer_amount.to_string(),
"msg": "",
})
.to_string()
.as_bytes(),
DEFAULT_GAS,
1,
);
res.assert_success();

// some-test-acc does not implement `ft_on_transfer` therefore the call fails and the transfer is reverted.
let balance = get_eth_on_near_balance(&master_account, DEPOSITED_RECIPIENT, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT - DEPOSITED_FEE);
let balance = get_eth_on_near_balance(&master_account, "some-test-acc", CONTRACT_ACC);
assert_eq!(balance, 0);
let balance = get_eth_on_near_balance(&master_account, CONTRACT_ACC, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_FEE);

// Sending to external receiver with empty message should be success
let dummy_ft_receiver = master_account.deploy(
&dummy_ft_receiver_bytes(),
"ft-rec".parse().unwrap(),
near_sdk_sim::STORAGE_AMOUNT,
);
let res = recipient_account.call(
CONTRACT_ACC.parse().unwrap(),
"ft_transfer_call",
json!({
"receiver_id": dummy_ft_receiver.account_id(),
"amount": transfer_amount.to_string(),
"msg": "",
})
.to_string()
.as_bytes(),
DEFAULT_GAS,
1,
);
res.assert_success();

let balance = get_eth_on_near_balance(&master_account, DEPOSITED_RECIPIENT, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT - DEPOSITED_FEE - transfer_amount);
let balance = get_eth_on_near_balance(
&master_account,
dummy_ft_receiver.account_id().as_ref(),
CONTRACT_ACC,
);
assert_eq!(balance, transfer_amount);
let balance = get_eth_on_near_balance(&master_account, CONTRACT_ACC, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_FEE);

let balance = get_eth_balance(
&master_account,
validate_eth_address(RECIPIENT_ETH_ADDRESS),
CONTRACT_ACC,
);
assert_eq!(balance, 0);

let balance = get_eth_balance(
&master_account,
validate_eth_address(CUSTODIAN_ADDRESS),
CONTRACT_ACC,
);
assert_eq!(balance, 0);

let balance = total_supply(&master_account, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT);

let balance = total_eth_supply_on_near(&master_account, CONTRACT_ACC);
assert_eq!(balance, DEPOSITED_AMOUNT);

let balance = total_eth_supply_on_aurora(&master_account, CONTRACT_ACC);
assert_eq!(balance, 0);
}

#[test]
fn test_deposit_with_same_proof() {
let (_master_account, contract) = init(CUSTODIAN_ADDRESS);
Expand Down Expand Up @@ -1269,3 +1401,11 @@ fn test_ft_transfer_wrong_u128_json_type() {
"Expected failure as number type can't be parsed to u128",
);
}

/// Bytes for a NEAR smart contract implementing `ft_on_transfer`
fn dummy_ft_receiver_bytes() -> Vec<u8> {
let base_path = std::path::Path::new("../etc").join("ft-receiver");
let output_path = base_path.join("target/wasm32-unknown-unknown/release/ft_receiver.wasm");
crate::test_utils::rust::compile(base_path);
std::fs::read(output_path).unwrap()
}
17 changes: 2 additions & 15 deletions engine-tests/src/tests/state_migration.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
use crate::prelude::U256;
use crate::test_utils::AuroraRunner;
use crate::test_utils::{self, AuroraRunner};
use aurora_engine::parameters::{InitCallArgs, NewCallArgs};
use borsh::BorshSerialize;
use near_sdk_sim::{ExecutionResult, UserAccount};
use std::fs;
use std::path::Path;
use std::process::Command;

#[test]
fn test_state_migration() {
Expand Down Expand Up @@ -90,18 +89,6 @@ fn contract_bytes() -> Vec<u8> {
let base_path = Path::new("../etc").join("state-migration-test");
let output_path = base_path
.join("target/wasm32-unknown-unknown/release/aurora_engine_state_migration_test.wasm");
compile(base_path);
test_utils::rust::compile(base_path);
fs::read(output_path).unwrap()
}

fn compile<P: AsRef<Path>>(source_path: P) {
let output = Command::new("cargo")
.current_dir(source_path)
.args(&["build", "--target", "wasm32-unknown-unknown", "--release"])
.output()
.unwrap();

if !output.status.success() {
panic!("{}", String::from_utf8(output.stderr).unwrap());
}
}
2 changes: 1 addition & 1 deletion engine/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "aurora-engine"
version = "2.0.2"
version = "2.1.0"
authors = ["NEAR <hello@near.org>"]
edition = "2018"
description = ""
Expand Down
42 changes: 23 additions & 19 deletions engine/src/connector.rs
Original file line number Diff line number Diff line change
Expand Up @@ -492,26 +492,30 @@ impl EthConnectorContract {
args.receiver_id, args.amount,
));
// Verify message data before `ft_on_transfer` call to avoid verification panics
let message_data = self.parse_on_transfer_message(&args.msg);
// Check is transfer amount > fee
assert!(
args.amount > message_data.fee.as_u128(),
"{}",
ERR_NOT_ENOUGH_BALANCE_FOR_FEE,
);
if args.receiver_id.as_bytes() == &sdk::current_account_id()[..] {
let message_data = self.parse_on_transfer_message(&args.msg);
// Check is transfer amount > fee
assert!(
args.amount > message_data.fee.as_u128(),
"{}",
ERR_NOT_ENOUGH_BALANCE_FOR_FEE,
);

// Additional check overflow before process `ft_on_transfer`
// But don't check overflow for relayer
// Note: It can't overflow because the total supply doesn't change during transfer.
let amount_for_check = self
.ft
.internal_unwrap_balance_of_eth_on_aurora(message_data.recipient);
assert!(amount_for_check.checked_add(args.amount).is_some());
assert!(self
.ft
.total_eth_supply_on_aurora
.checked_add(args.amount)
.is_some());
// Additional check overflow before process `ft_on_transfer`
// But don't check overflow for relayer
// Note: It can't overflow because the total supply doesn't change during transfer.
let amount_for_check = self
.ft
.internal_unwrap_balance_of_eth_on_aurora(message_data.recipient);
assert!(amount_for_check.checked_add(args.amount).is_some());

// It'll call only on Aurora contract
assert!(self
.ft
.total_eth_supply_on_aurora
.checked_add(args.amount)
.is_some());
}

self.ft
.ft_transfer_call(&args.receiver_id, args.amount, &args.memo, args.msg);
Expand Down
9 changes: 4 additions & 5 deletions engine/src/fungible_token.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use crate::connector::NO_DEPOSIT;
use crate::engine::Engine;
use crate::json::{parse_json, JsonValue};
use crate::parameters::{FtResolveTransfer, NEP141FtOnTransferArgs, StorageBalance};
use crate::parameters::{NEP141FtOnTransferArgs, ResolveTransferCallArgs, StorageBalance};
use crate::prelude::{
sdk, storage, str_from_slice, AccountId, Address, BTreeMap, Balance, BorshDeserialize,
BorshSerialize, EthAddress, Gas, PromiseResult, StorageBalanceBounds, StorageUsage, String,
Expand Down Expand Up @@ -232,16 +232,15 @@ impl FungibleToken {
let data1: String = NEP141FtOnTransferArgs {
amount,
msg,
sender_id: receiver_id.to_string(),
sender_id: sender_id.to_string(),
}
.try_into()
.unwrap();

let account_id = String::from_utf8(sdk::current_account_id()).unwrap();
let data2 = FtResolveTransfer {
let data2 = ResolveTransferCallArgs {
receiver_id: receiver_id.to_string(),
amount,
current_account_id: account_id,
sender_id: sender_id.to_string(),
}
.try_to_vec()
.unwrap();
Expand Down
Loading

0 comments on commit c4f4edb

Please sign in to comment.