Skip to content
This repository has been archived by the owner on Apr 15, 2020. It is now read-only.

Feature/146382715 metatx controller #38

Closed
wants to merge 58 commits into from

Conversation

naterush
Copy link
Contributor

This contains the first attempt at a singleton meta-tx relay contract. An overview, the design decisions, attacks, and thoughts about this can be found on this document: https://consensys.quip.com/CoClAjSTyBZI

Tests are very incomplete -- as of now, just test to make sure it works but not very thorough. Will be adding more in the coming days.

Would love some basic feedback on what exists so far.

pelle and others added 27 commits May 24, 2017 20:01
…ownership

Also don’t allow recoveryKey to overwrite existing owners
Fails due to various timestamp related issues
Added tests for migration. Would love some feedback on them :~)
This stops the following attack: 
Assume there is a single evil owner and any number of good owners. 
1. EO calls changeRecovery and changes the recovery to 0.
2. EO then calls forwardTo, and sends data through the proxy to the registerIdentity function in the IdentityManager.
3. In this forward, the EO provides a new ownerKey and a recoveryKey of 0 to the registerIdentity function. Thus, the conditional in the first line is false, and this does not throw.
4. The new owner is then added immediately with full power.
5. Thus, the evilOwner could effectively add a ton of new evil owners and overpower the good identity.
@oed
Copy link
Contributor

oed commented Jun 19, 2017

What is the reason for having a separate MetaTx contract? Wouldn't it make sense to put the metaTx verification directly into the MetaIdentityManager?
Another alternative is to have an abstract contract that the MetaIdentityManager inherits.
Anyway having yet another contract in the proxy call stack seems like bloat to me.

@naterush
Copy link
Contributor Author

@oed This is originally what @christianlundkvist did here: https://github.com/uport-project/uport-identity/blob/feature/identity-manager-metatx/contracts/IdentityManager.sol

That specific approach led to a lot of duplicated code, but I think you are right. Moving these functions into the MetaIdenitityManager itself seems like a good idea.

@naterush
Copy link
Contributor Author

naterush commented Jun 19, 2017

It's worth noting that a benefit of separating this into a separate contract is that it becomes a "singleton" meta-tx relay. All contracts that conform to the changes necessary for the relay (see here in the section "Changes to Existing Contracts:") are able to interact with it without having to add it to their code. This approach is likely very similar to an abstract contract, as you mentioned.

oed
oed previously requested changes Jul 7, 2017
/// @param owner Key who can use this contract to control proxy. Given full power
/// @param recoveryKey Key of recovery network or address from seed to recovery proxy
/// Gas cost of ~300,000
function CreateIdentity(address owner, address recoveryKey) validRecovery(recoveryKey) {
Copy link
Contributor

Choose a reason for hiding this comment

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

This method should start with a small caps letter.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@oed will update this now.

@naterush
Copy link
Contributor Author

naterush commented Jul 7, 2017

@oed These are good points, thanks. I'll work on doing this now. Any thoughts on what version of solc to go to? :)

@oed
Copy link
Contributor

oed commented Jul 7, 2017

@naterush The version supported by the latest truffle might be a good idea. Make sure to specify the truffle version without ^ so that we don't run in to errors due to this in the future.

@naterush naterush force-pushed the feature/146382715-metatx-controller branch from 8329461 to 4a95c63 Compare July 11, 2017 15:17
@coder5876
Copy link
Contributor

These changes look good to me, I.e. name change, updated solc and dependencies. 👍

@naterush naterush dismissed oed’s stale review July 11, 2017 16:05

Finished. Updated solc, and renamed.

* @param sigV, sigR, sigS ECDSA signature on some data to be forwarded
* @param data The bytes necessary to call the function in the destination contract.
Note, the first encoded argument in data must be address of the signer
* @param claimedSender Address of the user who is having tx forwarded
Copy link
Contributor

Choose a reason for hiding this comment

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

Does this need to be updated since it doesn't seem to be a direct Param?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@aldigjo good catch. Will update now.

//Checks that address a is the first input in msg.data.
//Has very minimal gas overhead.
function checkMessageData(address a) constant internal returns (bool t) {
if (msg.data.length < 36) return false;
Copy link
Contributor

Choose a reason for hiding this comment

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

Is this check really needed?

  1. Won't function calls fail if they don't match function signature?
  2. Won't the eq test return false (or throw?) if msg.data.lenth < 36?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I thought so also, but I had a test case that was failing b/c of this, somehow. Mabe should try to replicate, but I guess this does not really hurt.

Copy link
Contributor

Choose a reason for hiding this comment

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

hm, all tests work for me without that line. The only reason I ask is because solidity-coverage says that that line isn't covered, and I can't figure out a way to test it. But I guess it's fine to leave it there.

Copy link
Contributor

Choose a reason for hiding this comment

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

@naterush what was the original reason for the 36 magic number?

@oed anything else you feel need to be addressed? I'm eager to merge this one in.

Copy link
Contributor

Choose a reason for hiding this comment

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

@christianlundkvist nope, let's merge :)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@oed @christianlundkvist requires one more review, but it is probably good to get this out, so we can start testing.

@oed
Copy link
Contributor

oed commented Jul 18, 2017

It might be a good idea to add functions for isOwner and isRecovery as we currently have no way of checking this without trying to call another function and see if it fails.

@naterush
Copy link
Contributor Author

@oed happy to add when free on Thursday/Friday. Otherwise, if you want to merge sooner, feel free to add :~)

@coder5876
Copy link
Contributor

@oed @naterush I think it might also be good to have a mapping/function that takes a recovery key and returns the corresponding identity.

Also, the way we're doing actual recovery right now might open up an attack:

If I create a new identity with someone elses recoveryKey (that I don't control), then you might be able to block the recovery from that person.

@@ -208,4 +208,12 @@ contract IdentityManager {
t := eq(a, and(mask, calldataload(4)))
}
}

function isOwner(address identity, address user) constant returns (bool) {
Copy link
Contributor Author

Choose a reason for hiding this comment

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

User might be a little misleading langauge @oed. Maybe key (as below) would be better?

Copy link
Contributor

Choose a reason for hiding this comment

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

yeah, maybe change to owner and recoveryKey in the isRecovery function. Then it is consistant with everywhere else.

@naterush
Copy link
Contributor Author

@christianlundkvist Currently, the mapping is from identity => recoveryKey. This helper function would add an extra mapping (extra cost and thing to update, not sure it is worth it). Let me know what you think.

Also, not sure I follow the attack you describe. As the mapping is from identity => recovery key, couldn't multiple identities have the same recovery with no issue?

@oed oed force-pushed the feature/146382715-metatx-controller branch from 3de6310 to 0f15d2c Compare July 21, 2017 12:12
Copy link
Contributor

@pelle pelle left a comment

Choose a reason for hiding this comment

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

@naterush @oed we now need a separate IdentityManager for metaTx's so we can deploy them separately.

Copy link
Contributor

@pelle pelle left a comment

Choose a reason for hiding this comment

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

Really good. The meta tx code is pretty clear and isolated. So all we need is a separate MetaTxIdentityManager contract now and we should be good to go.

bytes32 h = sha3(this, nonce[claimedSender], destination, data, msg.sender);
address addressFromSig = ecrecover(h, sigV, sigR, sigS);

nonce[claimedSender]++;
Copy link
Contributor

Choose a reason for hiding this comment

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

@naterush I think it does make sense to move it below just for clarity.

if (b.length < 36) return address(0);
assembly {
let mask := 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
a := and(mask, mload(add(b, 36)))
Copy link
Contributor

Choose a reason for hiding this comment

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

Nice

import "./Proxy.sol";


contract IdentityManager {
Copy link
Contributor

Choose a reason for hiding this comment

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

@naterush @oed As I mentioned we need a new contract here. This may actually be a good candidate for inheritance as with the design here the only thing different is the constructor, onlyAuthorized and checkMessageData. That would also ensure that changes to the normal IdentityManager would get reflected here automatically.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I can rework this over the weekend. For a name, I think MetaIdentityManager works well.

Also, you mean just define a "ManagerInterface," right? If we do inheritance, I'm not sure we can just add modifiers on to functions (aka, would have to redefine functions anyway).

I do think it would make sense to make sure they share the same interface, though. Let me know what you think @pelle

@naterush
Copy link
Contributor Author

@pelle thanks. Will update this weekend. For the "I think it does make sense to move it below just for clarity," which line are you referring to?

//Validity Checks (if these throw this time, they will always throw)
if (claimedSender != addressFromSig) throw;
if (!checkAddress(data, addressFromSig)) throw;

Copy link
Contributor

Choose a reason for hiding this comment

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

@naterush move line 41 down here

Copy link
Contributor

Choose a reason for hiding this comment

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

Again just for clarity. I know the functionality is the same.

@pelle
Copy link
Contributor

pelle commented Aug 2, 2017

Consolidated and replaced by #45 and #17

@pelle pelle closed this Aug 2, 2017
@naterush naterush deleted the feature/146382715-metatx-controller branch November 15, 2017 22:14
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants