Skip to content

Commit

Permalink
Add blobhash high-level global function.
Browse files Browse the repository at this point in the history
  • Loading branch information
r0qs committed Jan 4, 2024
1 parent 69122e0 commit ff81045
Show file tree
Hide file tree
Showing 12 changed files with 86 additions and 6 deletions.
2 changes: 2 additions & 0 deletions libsolidity/analysis/GlobalContext.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ int magicVariableToID(std::string const& _name)
else if (_name == "tx") return -26;
else if (_name == "type") return -27;
else if (_name == "this") return -28;
else if (_name == "blobhash") return -29;
else
solAssert(false, "Unknown magic variable: \"" + _name + "\".");
}
Expand Down Expand Up @@ -91,6 +92,7 @@ inline std::vector<std::shared_ptr<MagicVariableDeclaration const>> constructMag
magicVarDecl("sha3", TypeProvider::function(strings{"bytes memory"}, strings{"bytes32"}, FunctionType::Kind::KECCAK256, StateMutability::Pure)),
magicVarDecl("suicide", TypeProvider::function(strings{"address payable"}, strings{}, FunctionType::Kind::Selfdestruct)),
magicVarDecl("tx", TypeProvider::magic(MagicType::Kind::Transaction)),
magicVarDecl("blobhash", TypeProvider::function(strings{"uint256"}, strings{"bytes32"}, FunctionType::Kind::BlobHash, StateMutability::View)),
// Accepts a MagicType that can be any contract type or an Integer type and returns a
// MagicType. The TypeChecker handles the correctness of the input and output types.
magicVarDecl("type", TypeProvider::function(
Expand Down
1 change: 1 addition & 0 deletions libsolidity/ast/Types.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3075,6 +3075,7 @@ std::string FunctionType::richIdentifier() const
case Kind::ABIEncodeCall: id += "abiencodecall"; break;
case Kind::ABIEncodeWithSignature: id += "abiencodewithsignature"; break;
case Kind::ABIDecode: id += "abidecode"; break;
case Kind::BlobHash: id += "blobhash"; break;
case Kind::MetaType: id += "metatype"; break;
}
id += "_" + stateMutabilityToString(m_stateMutability);
Expand Down
1 change: 1 addition & 0 deletions libsolidity/ast/Types.h
Original file line number Diff line number Diff line change
Expand Up @@ -1286,6 +1286,7 @@ class FunctionType: public Type
ABIEncodeWithSignature,
ABIDecode,
GasLeft, ///< gasleft()
BlobHash, ///< BLOBHASH
MetaType, ///< type(...)
/// Refers to a function declaration without calling context
/// (i.e. when accessed directly via the name of the containing contract).
Expand Down
6 changes: 6 additions & 0 deletions libsolidity/codegen/ExpressionCompiler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1460,6 +1460,12 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall)
case FunctionType::Kind::GasLeft:
m_context << Instruction::GAS;
break;
case FunctionType::Kind::BlobHash:
{
acceptAndConvert(*arguments[0], *function.parameterTypes()[0], true);
m_context << Instruction::BLOBHASH;
break;
}
case FunctionType::Kind::MetaType:
// No code to generate.
break;
Expand Down
8 changes: 8 additions & 0 deletions libsolidity/codegen/ir/IRGeneratorForStatements.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1663,6 +1663,14 @@ void IRGeneratorForStatements::endVisit(FunctionCall const& _functionCall)

break;
}
case FunctionType::Kind::BlobHash:
{
std::string args;
for (size_t i = 0; i < arguments.size(); ++i)
args += (args.empty() ? "" : ", ") + expressionAsType(*arguments[i], *(parameterTypes[i]));
define(_functionCall) << "blobhash(" << args << ")\n";
break;
}
default:
solUnimplemented("FunctionKind " + toString(static_cast<int>(functionType->kind())) + " not yet implemented");
}
Expand Down
16 changes: 10 additions & 6 deletions test/libsolidity/semanticTests/builtinFunctions/blobhash.sol
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
contract C {
function f() public view returns (bytes32 ret) {
assembly {
ret := blobhash(0)
}
function f() public view returns(bytes32) {
return blobhash(0);
}
function g() public view returns(bytes32) {
return blobhash(1);
}
function h() public view returns(bytes32) {
return blobhash(2);
}
}
// ====
// EVMVersion: >=cancun
// ----
// f() -> 0x0100000000000000000000000000000000000000000000000000000000000001
// g() -> 0x0100000000000000000000000000000000000000000000000000000000000002
// h() -> 0x00
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
contract C {
function blobhash(uint256 index) public pure returns(bytes32) {
return bytes32(index);
}
function f() public pure returns(bytes32) {
return blobhash(3);
}
}
// ====
// EVMVersion: >=cancun
// ----
// f() -> 0x03
11 changes: 11 additions & 0 deletions test/libsolidity/semanticTests/inlineAssembly/blobhash.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
contract C {
function f() public view returns (bytes32 ret) {
assembly {
ret := blobhash(0)
}
}
}
// ====
// EVMVersion: >=cancun
// ----
// f() -> 0x0100000000000000000000000000000000000000000000000000000000000001
14 changes: 14 additions & 0 deletions test/libsolidity/semanticTests/state/blobhash.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
contract C {
function f(uint _index) public returns (bytes32) {
return blobhash(_index);
}
}
// ====
// EVMVersion: >=cancun
// ----
// f(uint256): 0 -> 0x0100000000000000000000000000000000000000000000000000000000000001
// f(uint256): 1 -> 0x0100000000000000000000000000000000000000000000000000000000000002
// f(uint256): 2 -> 0x00
// f(uint256): 255 -> 0x00
// f(uint256): 256 -> 0x00
// f(uint256): 257 -> 0x00
9 changes: 9 additions & 0 deletions test/libsolidity/semanticTests/state/uncalled_blobhash.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
contract C {
function f() public returns (bytes32) {
return (blobhash)(0);
}
}
// ====
// EVMVersion: >=cancun
// ----
// f() -> 0x0100000000000000000000000000000000000000000000000000000000000001
12 changes: 12 additions & 0 deletions test/libsolidity/syntaxTests/blobhash_shadow_warning.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
contract C {
function blobhash(uint256 index) public pure returns(bytes32) {
return bytes32(index);
}
function f() public pure returns(bytes32) {
return blobhash(3);
}
}
// ====
// EVMVersion: >=cancun
// ----
// Warning 2319: (17-117): This declaration shadows a builtin symbol.

0 comments on commit ff81045

Please sign in to comment.