Fixes ICE when overriding an implemented modifier with an unimplemented one.

This commit is contained in:
Christian Parpart 2021-06-09 11:54:09 +02:00
parent 8de575f738
commit a14ac1923d
7 changed files with 63 additions and 8 deletions

View File

@ -31,6 +31,7 @@ Bugfixes:
* Type Checker: Fix internal compiler error when attempting to use an invalid external function type on pre-byzantium EVMs.
* Type Checker: Make errors about (nested) mapping type in event or error parameter into fatal type errors.
* Type Checker: Fix internal compiler error when overriding receive ether function with one having different parameters during inheritance.
* Type Checker: Fix internal compiler error when overriding an implemented modifier with an unimplemented one.
AST Changes:

View File

@ -573,6 +573,19 @@ void OverrideChecker::checkOverride(OverrideProxy const& _overriding, OverridePr
);
}
if (_overriding.unimplemented() && !_super.unimplemented())
{
solAssert(!_overriding.isVariable() || !_overriding.unimplemented(), "");
overrideError(
_overriding,
_super,
4593_error,
"Overriding an implemented " + _super.astNodeName() +
" with an unimplemented " + _overriding.astNodeName() +
" is not allowed."
);
}
if (_super.isFunction())
{
FunctionType const* functionType = _overriding.functionType();
@ -613,14 +626,6 @@ void OverrideChecker::checkOverride(OverrideProxy const& _overriding, OverridePr
stateMutabilityToString(_overriding.stateMutability()) +
"\"."
);
if (_overriding.unimplemented() && !_super.unimplemented())
overrideError(
_overriding,
_super,
4593_error,
"Overriding an implemented function with an unimplemented function is not allowed."
);
}
}

View File

@ -0,0 +1,11 @@
contract A {
modifier m() virtual { _; }
}
abstract contract B is A {
modifier m() virtual override;
}
contract C is B {
function f() m public {}
}
// ----
// TypeError 4593: (78-108): Overriding an implemented modifier with an unimplemented modifier is not allowed.

View File

@ -0,0 +1,11 @@
contract A {
modifier m() virtual { _; }
}
abstract contract B {
modifier m() virtual;
}
contract C is A, B {
modifier m() override(A, B) { _; }
function f() m public {}
}
// ----

View File

@ -0,0 +1,11 @@
abstract contract A {
modifier m() virtual;
}
abstract contract B is A {
modifier m() virtual override;
}
abstract contract C is B {
modifier m() virtual override;
function f() m public {}
}
// ----

View File

@ -0,0 +1,8 @@
abstract contract A {
modifier m() virtual;
function f() m public {}
}
contract B is A {
modifier m() virtual override { _; }
}
// ----

View File

@ -0,0 +1,8 @@
abstract contract A {
modifier m() virtual;
function f() m public virtual {}
}
abstract contract B is A {
function f() public override {}
}
// ----