offchainlabs / stylus-sdk-rs Goto Github PK
View Code? Open in Web Editor NEWRust Smart Contracts on Arbitrum
Rust Smart Contracts on Arbitrum
Issue:
sol! {
type Foo as uint32;
struct Bar {
Foo foo;
}
}
will fail to compile
Cause: alloy-sol-macro
transitive dependency v0.3.1 vs 0.3.2, former one generating such SolStruct
impl that it requires all fields to be SolStruct
s themselves, while latter one doesn't require it.
Yet, v0.3.2 cannot be picked by resolver. It requires syn-solidity = "0.3.2"
while latest stylus-proc
0.4.1 has strict requirement syn-solidity = "=0.3.1"
Proposed solution: relax requirement in stylus-proc
to syn-solidity = "0.3.1"
EDIT: Seems syn-solidity
was pinned due to breaking changes. While requirement can't be simply relaxed back, I'll leave this bug here.
Stylus version: 0.4.2
I have 3 contracts:
Erc20
is standard erc20 impl, I will omit the methods implementation, just mention the ones used test cases:
sol_storage! {
pub struct Erc20<T> {
mapping(address => uint256) balances;
mapping(address => mapping(address => uint256)) allowances;
uint256 total_supply;
PhantomData<T> phantom;
}
}
impl<T: Erc20Params> Erc20<T> {
pub fn mint(&mut self, account: Address, value: U256) -> Result<(), Erc20Error> { .... }
pub fn burn(&mut self, account: Address, value: U256) -> Result<(), Erc20Error> { ....}
pub fn update(&mut self, from: Address, to: Address, value: U256) -> Result<(), Erc20Error> { .... }
}
#[external]
impl<T: Erc20Params> Erc20<T> {
...
pub fn balance_of(&self, address: Address) -> Result<U256, Erc20Error> {
Ok(self.balances.get(address))
}
... (other methods are also implemented)
}
Erc20Burnable
is standard Erc20 extension link to solidity impl here
sol_storage! {
pub struct Erc20Burnable {
#[borrow]
Erc20<MyTokenParams> erc20;
}
}
#[external]
#[inherit(Erc20<MyTokenParams>)]
impl Erc20Burnable {
pub fn burn(&mut self, account: Address, amount: U256) -> Result<(), Erc20Error> {
self.erc20.burn(account, amount)
}
pub fn balance_of_burn(&self, address: Address) -> Result<U256, Erc20Error> {
Ok(self.erc20.balances.get(address))
}
}
MyToken
is the concreate contract impl that extends Erc20 and Erc20Burnable
sol_storage! {
#[entrypoint]
pub struct MyToken {
#[borrow]
Erc20<MyTokenParams> erc20;
#[borrow]
Erc20Burnable erc20_burnable;
}
}
#[external]
#[inherit(Erc20<MyTokenParams>, Erc20Burnable)]
impl MyToken {
pub fn mint(&mut self, account: Address, amount: U256) -> Result<(), Erc20Error> {
self.erc20.mint(account, amount)
}
pub fn balance_of_burn_erc(&self, address: Address) -> Result<U256, Erc20Error> {
self.erc20_burnable.balance_of_burn(address)
}
pub fn balance_of_direct(&self, address: Address) -> Result<U256, Erc20Error> {
Ok(self.erc20.balances.get(address))
}
}
After minting tokens with MyToken::mint(..) when trying to access balances from Erc20Burnable methods instead of actual value the call returns 0. It looks like it can not access right storage. Contract code is called correctly (I checked with throwing errors inside the Erc20 methods) but storage is not accessed in proper way.
simplified code (I'm using ether-rs but full test will take a lot of lines)
// balance taken with Erc20 balance_of method
let alice_balance = token.balance_of_burn(alice_address).call().await.unwrap();
// balance taken with call to Erc20Burnable method
let alice_balance_burn = token.balance_of_burn(alice_address).call().await.unwrap();
// balance taken from MyToken method calling Erc20Burnable method
let alice_balance_of_burn_erc = token.balance_of_burn_erc(alice_address).call().await.unwrap();
// balance taken from MyToken method directly reading Erc20 blances mapping
let alice_balance_of_direct = token.balance_of_direct(alice_address).call().await.unwrap();
All methods being called on Erc20Burnable
(value of alice_balance_burn, alice_balance_of_burn_erc
) are returning 0
It's quite unwieldy to inherit from a contract that makes a call to another contract, stemming from the fact that the parent contract isn't the entrypoint and thus doesn't implement TopLevelStorage
when it is being inherited from.
I've managed to work around this by manually implementing CallContext
(and StaticCallContext
, in my case) for the parent contract, but this feels hacky and easy to misappropriate.
From what I gather, the TopLevelStorage
trait is leveraged in this way to flush the storage cache in reentrant calls, but the inheritance situation I've laid out isn't really one of reentrancy...
I certainly lack some context on how the TopLevelStorage
trait is implemented and intended to be leveraged, but this feels like it should be possible without enabling the reentrant
flag
Hi there,
I'm trying to define an interface using the sol_interface!
macro, in which a function returns a custom type (struct).
Ideally, I would like to be able to use the sol!
macro from alloy-sol-types
to define my struct.
When I try this, for example:
use stylus_sdk::prelude::*;
use alloy_sol_types::sol;
sol! {
struct MyStruct {
uint256 myNum;
}
}
sol_interface! {
interface IMyInterface {
function doThing() returns (MyStruct);
}
}
I get the error:
proc macro panicked
message: not yet implemented: Solidity type SolChallenges is not yet implemented in sol_interface!
I dug around in the code a bit, and it seems that sol_interface!
can't interpret any struct
types.
The ability to do so (particularly in tandem with the sol!
macro) would be amazing, as currently, I believe my only option is to return a tuple type and manually deserialize it.
Stylus version: 0.4.2
This code does not compile:
sol_storage! {
pub struct Erc20Burnable<T> {
#[borrow]
Erc20<T> erc20;
}
}
I think it should, it represents an abstract class in Solidity with generic types
Note: without generic T
in struct declaration it works fine (eg.: when type is MyTokenParams struct that implements Erc20Params trait)
Stylus is missing ecrecover
function, or any alternative, used to verify typed data composed and signed according to EIP712 standard
cargo run --example counter
Compiling ethers-providers v2.0.9
Compiling ethers-contract-abigen v2.0.9
Compiling ethers-signers v2.0.9
Compiling alloy-sol-types v0.3.1
Compiling mio v0.8.8
error[E0432]: unresolved import `crate::sys::IoSourceState`
--> /Users/davirain/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.8/src/io_source.rs:12:5
|
12 | use crate::sys::IoSourceState;
| ^^^^^^^^^^^^^^^^^^^^^^^^^ no `IoSourceState` in `sys`
error[E0432]: unresolved import `crate::sys::tcp`
--> /Users/davirain/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.8/src/net/tcp/listener.rs:15:17
|
15 | use crate::sys::tcp::{bind, listen, new_for_addr};
| ^^^ could not find `tcp` in `sys`
error[E0432]: unresolved import `crate::sys::tcp`
--> /Users/davirain/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.8/src/net/tcp/stream.rs:13:17
|
13 | use crate::sys::tcp::{connect, new_for_addr};
| ^^^ could not find `tcp` in `sys`
error[E0433]: failed to resolve: could not find `Selector` in `sys`
--> /Users/davirain/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.8/src/poll.rs:300:18
I papre implement ibc protocol on arbitrum, but meet problem, does have any tutorials implment StorageType for Thtrid type, example Height, this is define, https://github.com/cosmos/ibc-rs/blob/dc8e4161dd5e00a2031cf3feb58dad1ed7e26bdb/crates/ibc/src/core/ics02_client/height.rs#L32
Stylus version: 0.4.2
We want to implement a classic MyToken contract that that inherits from Erc20
and change it's behavior by overriding the implementation of update(..)
virtual method from Erc20
.
Erc20
is implemented with OpenZeppelin code as reference (link here)
Solidity way:
abstract contract ERC20 {
//.....
function _update(address from, address to, uint256 value) internal virtual {
// function body
}
//other Erc20 functions
}
contract MyToken is ERC20, Pausable {
constructor {...}
function _update(address from, address to, uint256 value) internal virtual override {
// new logic goes here
// after new logic is executed we want to run base impl from ERC20
super._update(from, to, value);
}
}
To do the same with Stylus following structure hierarchy was defined:
sol_storage! {
pub struct Erc20<T> {
// here goes the erc20 fields
}
}
impl<T: Erc20Params> Erc20<T> {
pub fn update(&mut self, from: Address, to: Address, value: U256) -> Result<(), Vec<u8>> {
// method body
}
}
#[external]
impl<T: Erc20Params> Erc20<T> {
pub fn transfer(&mut self, to: Address, value: U256) -> Result<bool, Erc20Error> {
let owner = msg::sender();
self.transfer_internal(owner, to, value)?;
Ok(true)
}
fn transfer_internal(&mut self, from: Address, to: Address, value: U256) -> Result<(), Erc20Error> {
if from == Address::ZERO {
return Err(Erc20Error::Erc20InvalidSpender(Erc20InvalidSpender {
spender: Address::ZERO,
}));
}
if to == Address::ZERO {
return Err(Erc20Error::Erc20InvalidReceiver(Erc20InvalidReceiver {
receiver: Address::ZERO,
}));
}
self.update(from, to, value)
}
// other methods of Erc20
}
-------------- MyToken impl
sol_storage! {
#[entrypoint]
pub struct MyToken {
#[borrow]
Erc20<MyTokenParams> erc20;
}
}
impl MyToken {
pub fn update(&mut self, from: Address, to: Address, value: U256) -> Result<(), Vec<u8>> {
// new logic comes here
self.erc20.update(from, to, value)?;
Ok(())
}
}
#[external]
#[inherit(Erc20<MyTokenParams>)]
impl MyToken {
// body if MyToken
}
Expected behavior: when Erc20 methods call self.update(..) like in example above in transfer_internal(..)
method, execution goes to overridden function defined in MyToken impl
Current behavior: calling self.update(..)
inside transfer_internal(..)
executes the update(..)
from Erc20 impl
Tested to run the example with the latest version of alloy sol type and primitives, it doesn't build
Solidity supports contract constructors, yet Stylus doesn't. So contract developer is forced to invent some "initialized/not initialized" check and introduce distinct initialization method.
Is there an equivalent of Solidity constructor in Stylus? If not, is there any Stylus specific pattern you would suggest to achieve the same behavior?
I want to set a state variable to a value from msg
context or passed as an argument to the constructor. Sharing a simple example Solidity contract to illustrate.
contract Example {
address public owner;
uint256 public num;
constructor(uint256 _num) {
owner = msg.sender;
num = _num;
}
}
edit: I have found an example using init
function and initialized
variable. It still seems possible that someone frontruns you to call init
function (e.g. to become "owner" of the contract). Another example hardcodes the "owner" to prevent that.
edit2: I have just found the part about constructors here. I feel it might be helpful to have a link to it under "Developer reference" section.
In our in-house unit-testing abstractions (which are based on this PoC), we have tried to find a way to set msg::sender
. However, I think there is no way right now, because it is private to the SDK:
pub(crate) static mut SENDER: hostio::CachedOption<Address> = hostio::CachedOption::new(||{
let mut data = Address::ZERO;
unsafe {
hostio::msg_sender(data.as_mut_ptr())
};
data.into()
})
Could we make this pub
(though global mutable statics need to be treated with care) or is there a way to modify this I am missing?
Whenever you try to use the Call::new_in
API, Self
must be bound by TopLevelStorage + BorrowMut<Self>
, which means that you end up with a lot of &mut (impl TopLevelStorage + BorrowMut<Self>)
instead of a receiver argument.
This is not great, and would definitely be surprising to devs. It is my understanding that it is safe to do unsafe impl TopLevelStorage for X
where X
is used as a field of the entrypoint contract, and is marked as #[borrow]
. I think this is safe because when routing calls to the "sub-contract" (?), it effectively becomes the top-level storage because of #[borrow]
.
Is this mental model correct? Should this unsafe impl
block be handled by #[borrow]
?
stylus is using the same storage system as solidity so StorageMap is not iterable, but in some cases iterable map is very important and people always need to implement something like openzeppelin EnumerableMap
Currently for errors it's necessary to define an error within a sol!
block and also to impl fn from(err: Error) -> Vec<u8>
for each error to encode the error as a Solidity compatible error by calling .encode()
on the resulting error. To simplify this, a proc macro for #[derive(SolidityError)] should be defined.
OS: Windows 10 x64
Rust: 1.72.0
VS Build Tools 2022: 14.37.32822
cargo-stylus: 0.1.4
Steps to reproduce:
cargo stylus new fails-to-check
cd fails-to-check
cargo stylus check
Expected: check succeeds
Actual: check fails with
C:\Users\User\Projects\rust\banana>cargo stylus check
Compiling stylus-proc v0.2.0
error: linking with `link.exe` failed: exit code: 1120
|
= note: "C:\\Program Files\\Microsoft Visual Studio\\2022\\Community\\VC\\Tools\\MSVC\\14.37.32822\\bin\\HostX64\\x64\\link.exe" "/DEF:C:\\Users\\User\\AppData\\Local\\Temp\\rustcr8GcD6\\lib.def" "/NOLOGO" "C:\\Users\\User\\AppData\\Local\\Temp\\rustcr8GcD6\\symbols.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.00.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.01.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.02.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.03.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.04.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.05.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.06.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.07.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.08.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.09.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.10.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.11.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.12.rcgu.o" "C:\\Users\\User\\Projects\\ru13:37anana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.13.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.stylus_proc.83163f0ef4e4b294-cgu.14.rcgu.o" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.597j31fbz26ay48m.rcgu.rmeta" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.4344t86givcbs09f.rcgu.o" "/LIBPATH:C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps" "/LIBPATH:C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\liballoy_sol_types-5a259fff226a8c8d.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\liballoy_primitives-ad93b03a55794adf.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libbytes-2629ad7a6b9f5b39.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libitoa-d82fb866234c4626.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libtiny_keccak-d785abbb23dedae6.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libcrunchy-bd7b0301a3421ac9.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libhex_literal-1a07e78cb7103a90.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libconst_hex-cf762f4939371a55.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libcpufeatures-a362dc69d5aecbb1.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libcfg_if-68ed1fdf91f680d9.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libruint-11472cd88664c931.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libregex-26645200aa3c460a.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libregex_automata-a7795895a91c8ec6.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libaho_corasick-153ee297c3c4833a.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libmemchr-3b175fd84d47fb88.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libregex_syntax-b14ab3613e58f22f.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\liblazy_static-e5b7c24c07e81089.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libconvert_case-246738cad95f624f.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libunicode_segmentation-227882cd0f839168.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libsyn-6c640defbe227f11.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libsyn_solidity-2bcf61e580952b36.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libsyn-9593710509d5adab.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libsha3-d0a2bb5ae1657cfb.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libkeccak-caec9986c2e88504.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libdigest-9bb7c392faf6bf0e.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libblock_buffer-189cb1558a01866b.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libcrypto_common-14e9097dc4b7d81e.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libgeneric_array-2f51704f92b5a637.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libtypenum-d3806966f15e0878.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libquote-16664d29e1bc1113.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libproc_macro2-c573fdce701e4132.rlib" "C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\libunicode_ident-db62c766faf1da5b.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libproc_macro-7b90843133975eeb.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libstd-0f357f0f8e8eb48f.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libpanic_unwind-57325150de1d69ac.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\librustc_demangle-7a221d01d4c27fb2.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libstd_detect-7bffc6b402bc9229.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libhashbrown-3fd39796b57f4908.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\librustc_std_workspace_alloc-8572e8a98839f6d6.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libminiz_oxide-6e930372a69395c9.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libadler-ad696ea66c589e9d.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libunwind-0a3e7125dc6e7fef.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libcfg_if-7d7ae0874b44dfcc.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\liblibc-2e82681b8e87518e.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\liballoc-5ed5a0d27d7423da.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\librustc_std_workspace_core-e970d604d303b37d.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libcore-e73f27a013927059.rlib" "C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib\\libcompiler_builtins-fbb34b1faced902f.rlib" "kernel32.lib" "advapi32.lib" "bcrypt.lib" "kernel32.lib" "ntdll.lib" "userenv.lib" "ws2_32.lib" "kernel32.lib" "ws2_32.lib" "kernel32.lib" "msvcrt.lib" "/NXCOMPAT" "/LIBPATH:C:\\Users\\User\\.rustup\\toolchains\\stable-x86_64-pc-windows-msvc\\lib\\rustlib\\x86_64-pc-windows-msvc\\lib" "/OUT:C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.dll" "/OPT:REF,NOICF" "/DLL" "/IMPLIB:C:\\Users\\User\\Projects\\rust\\banana\\target\\release\\deps\\stylus_proc-b80a7200cb344d25.dll.lib" "/DEBUG:NONE"
= note: Creating library C:\Users\User\Projects\rust\banana\target\release\deps\stylus_proc-b80a7200cb344d25.dll.lib and object C:\Users\User\Projects\rust\banana\target\release\deps\stylus_proc-b80a7200cb344d25.dll.exp
liballoy_primitives-ad93b03a55794adf.rlib(alloy_primitives-ad93b03a55794adf.alloy_primitives.8ed169664c9e1a12-cgu.0.rcgu.o) : error LNK2019: unresolved external symbol native_keccak256 referenced in function _ZN16alloy_primitives5utils9keccak2569keccak25617hb59fee3098333425E
C:\Users\User\Projects\rust\banana\target\release\deps\stylus_proc-b80a7200cb344d25.dll : fatal error LNK1120: 1 unresolved externals
error: could not compile `stylus-proc` (lib) due to previous error
Stylus checks failed: failed to build project to WASM: cargo build command failed
Given the following contract:
sol_storage! {
pub struct Test {
uint8 t;
}
}
#[external]
impl Test {
pub fn getter(&mut self) -> U8 {
self.t.get()
}
pub fn setter(&mut self, t: U8) {
self.t.set(t)
}
}
we get this compiler error:
error[E0271]: type mismatch resolving `<IntBitCount<8> as SupportedInt>::Uint == Uint<8, 1>`
--> src/lib.rs:43:1
|
43 | #[external]
| ^^^^^^^^^^^ expected `Uint<8, 1>`, found `u8`
|
= note: expected struct `alloy_primitives::Uint<8, 1>`
found type `u8`
= note: required for `alloy_primitives::Uint<8, 1>` to implement `AbiType`
= note: required for `alloy_primitives::Uint<8, 1>` to implement `EncodableReturnType`
Given that Storage*
types use alloy_primitives
at the accessor boundaries I would expect the SDK to handle this conversion for contract boundaries for me. Note that U256
works fine.
I get the same error inside the SDK if we add this here:
test_type!(uint8, "uint8", Uint<8, 1>);
A simple workaround for now is to use Rust types at the contract boundaries and make the conversion explicit. In the above example, that would be something like:
pub fn getter(&mut self) -> u8 {
self.t.get().byte(0)
}
Enums are integral part of Rust language, so their support is necessary
I'd also suggest to support such features as explicit discriminant type and explicit tag numbers
The current template used to in cargo stylus new
contains [profile]
section in Cargo.toml
which makes it incompatible with workspaces. Since that template has .cargo/config.toml
anyway, it would be reasonable to move all profile settings there
Currently, stylus-sdk-rs
depends on alloy-primitives
and alloy-sol-types
version 0.3.1. This version contains a known EIP-712 nested struct hashing bug (alloy-rs/core#257).
Example: eip712_signing_hash
for Mail
produces an incorrect hash.
sol! {
struct Person {
string name;
address wallet;
}
struct Mail {
Person from;
Person to;
string contents;
}
}
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.