-
Notifications
You must be signed in to change notification settings - Fork 36.6k
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
p2p: Don't use timestamps from inbound peers for Adjusted Time #23631
Conversation
This makes it harder for others to tamper with our adjusted time.
Concept ACK |
Is this fixing #6071 ? |
Yes I think so, with SPV clients being inbound peers. |
Concept ACK I have been thinking "what could go wrong with this?" but can't find a realistic adverse scenario. Need to stare a bit more at the surrounding code before full ACK. What about this - a node fails to create outgoing connections while incoming connections arrive just fine (could happen due to a firewall or some other network mishap (intentional or not) or addrman filled with junk). Many incoming connections arrive from honest nodes with correct times, which are ignored. How realistic is that? Is it worth considering an extension of this patch that starts collecting time samples from incoming connections if none or very few samples have been collected from outgoing connections for a long time after startup? |
I've never heard of someone in this situation this before, maybe others have?
My first reaction was that this situation is so unlikely that it wouldn't be worth the extra complexity, but I'd love to hear other opinions! |
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.
tentative Concept ACK. The motivation sounds good to me although i'm not very familiar with this code.
Concept and code review ACK 0c85dc3 |
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.
@@ -2683,7 +2683,11 @@ void PeerManagerImpl::ProcessMessage(CNode& pfrom, const std::string& msg_type, | |||
|
|||
int64_t nTimeOffset = nTime - GetTime(); | |||
pfrom.nTimeOffset = nTimeOffset; | |||
AddTimeData(pfrom.addr, nTimeOffset); | |||
if (!pfrom.IsInboundConn()) { |
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.
nit, feel free to ignore: there is already if (!pfrom.IsInboundConn()) {
just a few lines above and the nTimeOffset
local variable seems unnecessary.
dont click here
--- i/src/net_processing.cpp
+++ w/src/net_processing.cpp
@@ -2657,47 +2657,48 @@ void PeerManagerImpl::ProcessMessage(CNode& pfrom, const std::string& msg_type,
if (!pfrom.IsInboundConn()) {
// For non-inbound connections, we update the addrman to record
// connection success so that addrman will have an up-to-date
// notion of which peers are online and available.
//
// While we strive to not leak information about block-relay-only
// connections via the addrman, not moving an address to the tried
// table is also potentially detrimental because new-table entries
// are subject to eviction in the event of addrman collisions. We
// mitigate the information-leak by never calling
// AddrMan::Connected() on block-relay-only peers; see
// FinalizeNode().
//
// This moves an address from New to Tried table in Addrman,
// resolves tried-table collisions, etc.
m_addrman.Good(pfrom.addr);
+
+ // Don't use timedata samples from inbound peers to make it
+ // harder for others to tamper with our adjusted time.
+ pfrom.nTimeOffset = nTime - GetTime();
+ AddTimeData(pfrom.addr, pfrom.nTimeOffset);
}
std::string remoteAddr;
if (fLogIPs)
remoteAddr = ", peeraddr=" + pfrom.addr.ToString();
LogPrint(BCLog::NET, "receive version message: %s: version %d, blocks=%d, us=%s, txrelay=%d, peer=%d%s\n",
cleanSubVer, pfrom.nVersion,
peer->m_starting_height, addrMe.ToString(), fRelay, pfrom.GetId(),
remoteAddr);
- int64_t nTimeOffset = nTime - GetTime();
- pfrom.nTimeOffset = nTimeOffset;
- AddTimeData(pfrom.addr, nTimeOffset);
-
// If the peer is old enough to have the old alert system, send it the final alert.
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.
That suggested patch would leave pfrom.nTimeOffset
unset for inbound peers, which in turn would mean that timeoffset
is unset in the node stats.
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.
Right!
I think the justification makes sense and the code is good. This is an improvement.
Yeah, it's hard for me to imagine this, I can only see this happen if Addrman is attacked in a very severe way sometime during node uptime. And even in that case i don't think this current approach can help much. |
… Adjusted Time 0c85dc3 p2p: Don't use timestamps from inbound peers (Martin Zumsande) Pull request description: `GetAdjustedTime()` (used e.g. in validation and addrman) returns a time with an offset that is influenced by timestamps that our peers have sent us in their version message. Currently, timestamps from all peers are used for this. However, I think that it would make sense to ignore the timedata samples from inbound peers, making it much harder for others to influence the Adjusted Time in a targeted way. With the extra feeler connections (every 2 minutes on average) and extra block-relay-only connections (every 5 minutes on average) there are also now plenty of opportunities to gather a meaningful number of timedata samples from outbound peers. There are some measures in place to prevent abuse: the `-maxtimeadjustment` parameter with a default of 70 minutes, warnings in cases of large deviations, only using the first 200 samples ([explanation](https://github.com/bitcoin/bitcoin/blob/383d350bd5107bfe00e3b90a00cab9a3c1397c72/src/timedata.cpp#L57-L72)), but I think that only using samples from outbound connections in the first place would be an additional safety measure that would make sense. See also issue bitcoin#4521 for further context and links: There have been several discussions in the past about replacing or abolishing the existing timedata system. ACKs for top commit: jnewbery: Concept and code review ACK 0c85dc3 naumenkogs: ACK 0c85dc3 vasild: ACK 0c85dc3 Tree-SHA512: 2d6375305bcae034d68b58b7a07777b40ac430dfed554c88e681a048c527536691e1b7d08c0ef995247d356f8e81aa0a4b983bf2674faf6a416264e5f1af0a96
…eers for Adjusted Time 04f4770 p2p: Don't use timestamps from inbound peers (Martin Zumsande) Pull request description: `GetAdjustedTime()` (used e.g. in validation and addrman) returns a time with an offset that is influenced by timestamps that our peers have sent us in their version message. Currently, timestamps from all peers are used for this. However, I think that it would make sense to ignore the timedata samples from inbound peers, making it much harder for others to influence the Adjusted Time in a targeted way. With the extra feeler connections (every 2 minutes on average) and extra block-relay-only connections (every 5 minutes on average) there are also now plenty of opportunities to gather a meaningful number of timedata samples from outbound peers. There are some measures in place to prevent abuse: the `-maxtimeadjustment` parameter with a default of 70 minutes, warnings in cases of large deviations, only using the first 200 samples ([explanation](https://github.com/bitcoin/bitcoin/blob/b63551cc4a6cda8f7af3ad5560b97cdb14ce5b67/src/timedata.cpp#L57-L72)), but I think that only using samples from outbound connections in the first place would be an additional safety measure that would make sense. See also issue #4521 for further context and links: There have been several discussions in the past about replacing or abolishing the existing timedata system. ACKs for top commit: jnewbery: Concept and code review ACK 04f4770 naumenkogs: ACK 04f4770 vasild: ACK 04f4770 Tree-SHA512: 2d6375305bcae034d68b58b7a07777b40ac430dfed554c88e681a048c527536691e1b7d08c0ef995247d356f8e81aa0a4b983bf2674faf6a416264e5f1af0a96
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.
…ers influence timedata 1bba72d Clarify in -maxtimeadjustment that only outbound peers influence time data (Jon Atack) Pull request description: bitcoin#23631 changed our adjusted time to only take into account time from outbound peers. Update `-maxtimeadjustment` to clarify this for users. ACKs for top commit: MarcoFalke: cr ACK 1bba72d mzumsande: code Review ACK 1bba72d brunoerg: crACK 1bba72d Tree-SHA512: ad610ab3038fb83134e21d31cca952ef9ac926e88992ff93023b7010f2499f9a4d952e8e98a0ec56f8949872d966e5ffdd01a81e6b6115768f1992bd81be7a56
…ers influence timedata 1bba72d Clarify in -maxtimeadjustment that only outbound peers influence time data (Jon Atack) Pull request description: bitcoin#23631 changed our adjusted time to only take into account time from outbound peers. Update `-maxtimeadjustment` to clarify this for users. ACKs for top commit: MarcoFalke: cr ACK 1bba72d mzumsande: code Review ACK 1bba72d brunoerg: crACK 1bba72d Tree-SHA512: ad610ab3038fb83134e21d31cca952ef9ac926e88992ff93023b7010f2499f9a4d952e8e98a0ec56f8949872d966e5ffdd01a81e6b6115768f1992bd81be7a56
Summary: > This makes it harder for others to tamper with our adjusted time. Rationale from the PR description: > With the extra feeler connections (every 2 minutes on average) and extra block-relay-only connections (every 5 minutes on average) there are also now plenty of opportunities to gather a meaningful number of timedata samples from outbound peers. > > There are some measures in place to prevent abuse: the -maxtimeadjustment parameter with a default of 70 minutes, warnings in cases of large deviations, only using the first 200 samples (explanation), but I think that only using samples from outbound connections in the first place would be an additional safety measure that would make sense. > > See also issue [[bitcoin/bitcoin#4521 | core#4521]] for further context and links: There have been several discussions in the past about replacing or abolishing the existing timedata system. The difference with the source material is caused by D6024. This changes previous behavior slightly: now the computed time offset is assigned to the node even if we are not going to use it to compute our adjusted time. This `pfrom.nTimeOffset` is only used for display purposes (RPC results, GUI). This is a backport of [[bitcoin/bitcoin#23631 | core#23631]] Depends on D13357 Test Plan: `ninja all check-all` Reviewers: #bitcoin_abc, Fabien Reviewed By: #bitcoin_abc, Fabien Subscribers: Fabien Differential Revision: https://reviews.bitcoinabc.org/D13357
GetAdjustedTime()
(used e.g. in validation and addrman) returns a time with an offset that is influenced by timestamps that our peers have sent us in their version message.Currently, timestamps from all peers are used for this.
However, I think that it would make sense to ignore the timedata samples from inbound peers, making it much harder for others to influence the Adjusted Time in a targeted way.
With the extra feeler connections (every 2 minutes on average) and extra block-relay-only connections (every 5 minutes on average) there are also now plenty of opportunities to gather a meaningful number of timedata samples from outbound peers.
There are some measures in place to prevent abuse: the
-maxtimeadjustment
parameter with a default of 70 minutes, warnings in cases of large deviations, only using the first 200 samples (explanation), but I think that only using samples from outbound connections in the first place would be an additional safety measure that would make sense.See also issue #4521 for further context and links: There have been several discussions in the past about replacing or abolishing the existing timedata system.