notes: how a secret is sharded and returned
A primary peer creates shard messages for all holders. each shard message is encrypted to the holder and the primary,
but then the shard inside of that is again encrypted only to the holder. This means the primary forgets the shards.
You can decrypt the outer (and so see who you sent shards too) but not regain the shard.
following key compromise, compromiser knowns who holds shards (this may be considered necessary...)
When you request the shards back, a private request is sent to each holder. They then decrypt the shard from the previous message, and then send it back. https://github.com/blockades/scuttle-dark-crystal/blob/master/recover/async/reply.js#L61-L62
{
root, branch, accept: true,
body: decrypted_shard,
recps: [primary, holder]
}
The shard is decrypted and sent back to the primary. the holder does not forget the shard. future key compromise of a qorum of holders can recover the secret
But worse: the shards are now on permanent logs encrypted to the primary - so after recovery, future compromise of the holder can recover the secret. However, key compromise before recovery does not reveal the secret, but after recovery it does.
It seems unfortunate that dark-crystal goes to a special effort to avoid logging the shards, but then looses that property after recovery. In particular, for backing up a cryptocurrency private key, it would be better not to have that private key on the log.
mitigation: with current design, a dark-crystal user should move all funds from the recovered wallet to a new address after recovery. However, this is not obvious and they'll probably forget.
remediation: internal forward-secrecy as suggested above for revoking trust would also fix this problem.
("mitigation" and "remediation" are auditing terms - mitigation is what users can currently do to reduce or avoid the problem, "remediation" is how the problem can be fixed by a change to the system)