Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat/operators #28

Draft
wants to merge 26 commits into
base: dev
Choose a base branch
from
Draft

Feat/operators #28

wants to merge 26 commits into from

Conversation

0xShaito
Copy link
Member

@0xShaito 0xShaito commented Sep 9, 2024

🤖 Linear

Closes GRT-XXX

@0xShaito 0xShaito changed the base branch from dev to feat/slashing September 10, 2024 18:06
Copy link
Contributor

@ashitakah ashitakah left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would like to know where the users authorize a valid operator. I guess that have to be in horizon staking. My question here is: Is there any way that another user authorize a malicious operator? Except that, the code looks solid

revert HorizonAccountingExtension_UnauthorizedOperator();
}
_bonder = _operator;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like this one

@@ -241,54 +274,40 @@ contract HorizonAccountingExtension is Validator, IHorizonAccountingExtension {
});
}

/// @inheritdoc IHorizonAccountingExtension
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why this is deleted?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's only called by the BondEscalationResolutionModule (which we don't use)

src/interfaces/IHorizonAccountingExtension.sol Outdated Show resolved Hide resolved
// [ ] 5. Bonder or operator should be able to remove the operator
// [ ] 6. Can a bonder have an operator and mix calls by the operator and themselves?
// [ ] 7. Can a bonder that has an operator be an operator for another address?
mapping(address _operator => address _bonder) public operators;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The mapping returns bonders, not operators. Rename to operatedBonders maybe.

Comment on lines +68 to +69
// RULES:
// [X] 1. Operator can only operate for one bonder at a time
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This rule is both limiting and conflicting, as an operator cannot act on behalf of many bonders at the same time even though he may be allowed as such per HorizonStaking.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would mix all of the pledges otherwise and would be impossible to pay/slash the bonders. Do you think there could be a way to fix it?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Problem would be that we wouldn't be able to retrieve on behalf of which bonder an operator is acting, unless we modified a bunch of Prophet's interfaces. No easy way out.

Comment on lines +442 to +443
// TODO: To calculate the amount of pledges, we need to check for both
// the bonder and the operator. How should we do this?
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Take into account that a bonder may have set many operators to act on behalf of him.

Comment on lines 74 to 75
// [ ] 6. Can a bonder have an operator and mix calls by the operator and themselves?
// [ ] 7. Can a bonder that has an operator be an operator for another address?
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

// [ ] 8. Can an operator be a bonder?
// [ ] 9. Can an operator that is a bonder have an operator?
// [ ] 10. Can an operator that is a bonder have an operator that is a bonder?

All these last points may happen desiredly, so they should be carefully tested.

Comment on lines +483 to +491
function _getBonder(address _caller) internal view returns (address _bonder) {
address _operator = operators[_caller];
if(_operator == address(0)) {
_bonder = _caller;
} else {
if(!HORIZON_STAKING.isAuthorized(_caller, _operator, address(this))) {
revert HorizonAccountingExtension_UnauthorizedOperator();
}
_bonder = _operator;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What if a bonder is also an operator but wants to act on his own behalf? There's no way to distinguish this in the current implementation, but there's a precedence of the operator role over the bonder one.

Comment on lines 64 to 65
// TODO: Pledgers holds either the bonder or the operator.
mapping(bytes32 _disputeId => EnumerableSet.AddressSet _pledger) internal _pledgers;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be great if we didn't need to store the operators, as they aren't going to be the ones potentially getting slashed.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The problem is that the amount of pledges it stored in the operators name and not the bonder. To slash the bonder first we need to get the amount of pledges the operator made

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why isn't BondEscalationAccounting the one tracking pledgesForDispute and pledgesAgainstDispute in the first place, instead of BondEscalationModule?

TODO: To calculate the amount of pledges, we need to check for both the bonder and the operator. How should we do this?

The above is my answer. By implementing it, we could get rid of bonderForRequest, bonderForDispute, and HorizonAccountingExtension_BonderMismatch.

Comment on lines 408 to 409
// Check if the user is actually slashable
_slashAmount = _calculateSlashAmount(_user, _result, _status);
_slashAmount = _calculateSlashAmount(_pledger, _result, _status);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The _pledger may hold an operator whose address you shouldn't use to calculate the _slashAmount.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The pledge is made by the operator so it's stored for them in the BondEscalationModule

Comment on lines +380 to +385
function operateFor(address _bonder) external {
// TODO: Include a function to remove the operator callable by the operator or the bonder
if(!HORIZON_STAKING.isAuthorized(msg.sender, _bonder, address(this))) {
revert HorizonAccountingExtension_UnauthorizedOperator();
}
operators[msg.sender] = _bonder;
Copy link
Member

@0xJabberwock 0xJabberwock Sep 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Letting operators call this as is introduces the hazard of a race condition during the execution sequence for a same bonder; forbid sluggish authorized operators to interact.

TODO: Include a function to remove the operator callable by the operator or the bonder

I don't think such function is useful: a set operator may already change his bonder at any time if authorized by another, and if not, an idle operator doesn't hurt the bonder, who may have more operators set.

Comment on lines 64 to 65
// TODO: Pledgers holds either the bonder or the operator.
mapping(bytes32 _disputeId => EnumerableSet.AddressSet _pledger) internal _pledgers;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why isn't BondEscalationAccounting the one tracking pledgesForDispute and pledgesAgainstDispute in the first place, instead of BondEscalationModule?

TODO: To calculate the amount of pledges, we need to check for both the bonder and the operator. How should we do this?

The above is my answer. By implementing it, we could get rid of bonderForRequest, bonderForDispute, and HorizonAccountingExtension_BonderMismatch.

Comment on lines 283 to 284
) external onlyAllowedModule(_requestId) onlyParticipant(_requestId, _payer) onlyParticipant(_requestId, _receiver) {
// TODO: Validate participants against bonders
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why? The participants registered in the Oracle must be the requester, proposer and disputer, who may not be bonders.

Base automatically changed from feat/slashing to dev September 19, 2024 15:34
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants