diff --git a/graph/src/data/store/scalar/bigint.rs b/graph/src/data/store/scalar/bigint.rs index c344ec83a6d..526ca5ba390 100644 --- a/graph/src/data/store/scalar/bigint.rs +++ b/graph/src/data/store/scalar/bigint.rs @@ -1,3 +1,4 @@ +use anyhow::bail; use num_bigint; use serde::{self, Deserialize, Serialize}; use stable_hash::utils::AsInt; @@ -207,14 +208,15 @@ impl BigInt { } } - pub fn to_unsigned_u256(&self) -> U256 { + pub fn to_unsigned_u256(&self) -> Result { let (sign, bytes) = self.to_bytes_le(); - assert!( - sign == BigIntSign::NoSign || sign == BigIntSign::Plus, - "negative value encountered for U256: {}", - self - ); - U256::from_little_endian(&bytes) + if sign != BigIntSign::Plus && sign != BigIntSign::NoSign { + bail!( + "BigInt value is negative, cannot convert to unsigned U256: {}", + self + ); + } + Ok(U256::from_little_endian(&bytes)) } pub fn pow(self, exponent: u8) -> Result { diff --git a/graph/src/data_source/common.rs b/graph/src/data_source/common.rs index 344253cebdf..f89739c6ab7 100644 --- a/graph/src/data_source/common.rs +++ b/graph/src/data_source/common.rs @@ -668,7 +668,7 @@ impl CallDecl { (ParamType::Int(_), Value::BigInt(i)) => Ok(Token::Int(i.to_signed_u256())), (ParamType::Uint(_), Value::Int(i)) if *i >= 0 => Ok(Token::Uint((*i).into())), (ParamType::Uint(_), Value::BigInt(i)) if i.sign() == Sign::Plus => { - Ok(Token::Uint(i.to_unsigned_u256())) + Ok(Token::Uint(i.to_unsigned_u256()?)) } (ParamType::Array(inner_type), Value::List(values)) => { self.process_entity_array_values(values, inner_type.as_ref(), param_name) diff --git a/runtime/test/src/test/abi.rs b/runtime/test/src/test/abi.rs index 422bd25b2d1..336e8e5eacf 100644 --- a/runtime/test/src/test/abi.rs +++ b/runtime/test/src/test/abi.rs @@ -515,7 +515,7 @@ async fn test_abi_big_int(api_version: Version) { .await; let new_uint: BigInt = module.asc_get(new_uint_obj).unwrap(); assert_eq!(new_uint, BigInt::from(1_i32)); - let new_uint = new_uint.to_unsigned_u256(); + let new_uint = new_uint.to_unsigned_u256().unwrap(); assert_eq!(new_uint, U256([1, 0, 0, 0])); // Test passing in -50 and increment it by 1 diff --git a/runtime/wasm/src/to_from/external.rs b/runtime/wasm/src/to_from/external.rs index ca9f994d8a9..022c07b0bc8 100644 --- a/runtime/wasm/src/to_from/external.rs +++ b/runtime/wasm/src/to_from/external.rs @@ -243,7 +243,10 @@ impl FromAscObj> for ethabi::Token { EthereumValueKind::Uint => { let ptr: AscPtr = AscPtr::from(payload); let n: BigInt = asc_get(heap, ptr, gas, depth)?; - Token::Uint(n.to_unsigned_u256()) + let uint = n + .to_unsigned_u256() + .map_err(DeterministicHostError::Other)?; + Token::Uint(uint) } EthereumValueKind::String => { let ptr: AscPtr = AscPtr::from(payload);