-
Notifications
You must be signed in to change notification settings - Fork 106
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
Security: stop gossiping failure and attempt times as last_seen times #2273
Conversation
Previously, Zebra had a single time field for peer addresses, which was updated every time a peer was attempted, sent a message, or failed. This is a security issue, because the `last_seen` time should be "the last time [a peer] connected to that node", so that "nodes can use the time field to avoid relaying old 'addr' messages". So Zebra was sending incorrect peer information to other nodes. As part of this change, we split the `last_seen` time into the following fields: - untrusted_last_seen: gossiped from other peers - last_response: time we got a response from a directly connected peer - last_attempt: time we attempted to connect to a peer - last_failure: time a connection with a peer failed
I still need to write proptests to ensure:
|
Also replace the MetaAddr Arbitrary impl with a derive.
MetaAddr: - the only times that get included in serialized MetaAddrs are the untrusted last seen and responded times MetaAddrChange: - the untrusted last seen time is never updated - the services are only updated if there has been a handshake
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's looking good! I added a few suggestions and questions.
I updated the PR description, changing |
Thanks for catching that! |
- make ready_outbound_strategy generate changes - update existing strategies based on the refactor - update newly added proptests based on the refactor
…#2273) * Security: stop gossiping failure and attempt times as last_seen times Previously, Zebra had a single time field for peer addresses, which was updated every time a peer was attempted, sent a message, or failed. This is a security issue, because the `last_seen` time should be "the last time [a peer] connected to that node", so that "nodes can use the time field to avoid relaying old 'addr' messages". So Zebra was sending incorrect peer information to other nodes. As part of this change, we split the `last_seen` time into the following fields: - untrusted_last_seen: gossiped from other peers - last_response: time we got a response from a directly connected peer - last_attempt: time we attempted to connect to a peer - last_failure: time a connection with a peer failed * Implement Arbitrary and strategies for MetaAddrChange Also replace the MetaAddr Arbitrary impl with a derive. * Write proptests for MetaAddr and MetaAddrChange MetaAddr: - the only times that get included in serialized MetaAddrs are the untrusted last seen and responded times MetaAddrChange: - the untrusted last seen time is never updated - the services are only updated if there has been a handshake
…#2273) * Security: stop gossiping failure and attempt times as last_seen times Previously, Zebra had a single time field for peer addresses, which was updated every time a peer was attempted, sent a message, or failed. This is a security issue, because the `last_seen` time should be "the last time [a peer] connected to that node", so that "nodes can use the time field to avoid relaying old 'addr' messages". So Zebra was sending incorrect peer information to other nodes. As part of this change, we split the `last_seen` time into the following fields: - untrusted_last_seen: gossiped from other peers - last_response: time we got a response from a directly connected peer - last_attempt: time we attempted to connect to a peer - last_failure: time a connection with a peer failed * Implement Arbitrary and strategies for MetaAddrChange Also replace the MetaAddr Arbitrary impl with a derive. * Write proptests for MetaAddr and MetaAddrChange MetaAddr: - the only times that get included in serialized MetaAddrs are the untrusted last seen and responded times MetaAddrChange: - the untrusted last seen time is never updated - the services are only updated if there has been a handshake
Motivation
Previously, Zebra had a single time field for each peer, which was updated every time a peer was attempted, sent a message, or failed.
This is a security issue, because the
last_seen
time should be "the last time [a peer] connected to that node", so that"nodes can use the time field to avoid relaying old 'addr' messages".
So Zebra was sending incorrect peer times to other nodes, which is malicious behaviour.
Specifications
addr.time field description:
https://developer.bitcoin.org/reference/p2p_networking.html#addr
Designs
This PR uses the
DateTime32
type introduced in PR #2210, see ticket #2171 for more details.Solution
Security Changes
Other Required Changes
Split the
last_seen
time into the following fields:DateTime32
DateTime32
Instant
Instant
Send peer changes using a new
MetaAddrChange
type, so that senders don't accidentally overwrite peer fields with outdated data. (Due to concurrency, changes can be applied to the address book out of order.)Review
@jvff can review this PR. It's an important security fix, but it's not particularly urgent.
This PR should close #1868.
Reviewer Checklist
Follow Up Work
This PR is part of a series of MetaAddr refactors.
After #1867 is fixed, the network will be able to remove the unreachable addresses introduced by #2120.