Library function can be used as user operator

This commit is contained in:
wechman 2022-07-28 08:42:39 +02:00
parent 7d12eb5745
commit e8243d49bc
3 changed files with 43 additions and 4 deletions

View File

@ -413,7 +413,10 @@ bool ExpressionCompiler::visit(UnaryOperation const& _unaryOperation)
if (FunctionDefinition const* function = _unaryOperation.annotation().userDefinedFunction)
{
solAssert(function->isFree(), "Only free functions can be bound to a user type operator.");
solAssert(
function->isFree() || function->libraryFunction(),
"Only file-level functions and library functions can be bound to a user type operator."
);
FunctionType const* functionType = dynamic_cast<FunctionType const*>(
function->libraryFunction() ? function->typeViaContractName() : function->type()
@ -537,7 +540,10 @@ bool ExpressionCompiler::visit(BinaryOperation const& _binaryOperation)
Expression const& rightExpression = _binaryOperation.rightExpression();
if (FunctionDefinition const* function =_binaryOperation.annotation().userDefinedFunction)
{
solAssert(function->isFree(), "Only free function can be bound to a user type operator.");
solAssert(
function->isFree() || function->libraryFunction(),
"Only file-level functions and library functions can be bound to a user type operator."
);
FunctionType const* functionType = dynamic_cast<FunctionType const*>(
function->libraryFunction() ? function->typeViaContractName() : function->type()
);

View File

@ -679,7 +679,7 @@ bool IRGeneratorForStatements::visit(UnaryOperation const& _unaryOperation)
setLocation(_unaryOperation);
solAssert(
dynamic_cast<SourceUnit const*>(function->scope()),
function->isFree() || function->libraryFunction(),
"Only file-level functions and library functions can be bound to a user type operator."
);
@ -824,7 +824,7 @@ bool IRGeneratorForStatements::visit(BinaryOperation const& _binOp)
setLocation(_binOp);
solAssert(
dynamic_cast<SourceUnit const*>(function->scope()),
function->isFree() || function->libraryFunction(),
"Only file-level functions and library functions can be bound to a user type operator."
);

View File

@ -0,0 +1,33 @@
==== Source: a.sol ====
library L {
type Int is int128;
function add(Int, Int) pure public returns (Int) {
return Int.wrap(7);
}
function sub(Int) pure public returns (Int) {
return Int.wrap(5);
}
}
==== Source: b.sol ====
import "a.sol" as a;
contract C {
using {a.L.add as +} for a.L.Int;
using {a.L.sub as -} for a.L.Int;
function f() pure public returns (a.L.Int) {
return a.L.Int.wrap(0) + a.L.Int.wrap(0);
}
function g() pure public returns (a.L.Int) {
return - a.L.Int.wrap(0);
}
}
// ====
// compileViaYul: also
// ----
// f() -> 7
// g() -> 5