-
Notifications
You must be signed in to change notification settings - Fork 38.6k
Well-defined CAddress disk serialization, and addrv2 anchors.dat #20516
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
Conversation
|
The following sections might be updated with supplementary metadata relevant to reviewers and maintainers. ConflictsReviewers, this pull request conflicts with the following ones:
If you consider this pull request important, please also help to review the conflicting pull requests. Ideally, start with the one that should be merged first. |
94fdec1 to
1991447
Compare
1991447 to
04e3733
Compare
|
I merged the anchors.dat addrv2 support from #20514 into this PR, as doing it correctly requires changes the |
|
Concept ACK. From the PR description and quick code reading it follows that there is no hurry to backport these changes into 0.21, right? |
|
Indeed, there is probably no hurry, unless we want to support torv3 anchors in 0.21. |
hebasto
left a comment
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.
In commit 6d16903c4c384bc15f3f29e5635bb9dccd789cb6 message:
These do no introduce incompatibilities, as no code versions exist that write
any value other than 0 or 0x20000000 in the top 19 bits, and no code paths
where the stream's version differs from the stored version.
s/top 19/high 13/ ?
22b8c55 to
80f5c54
Compare
|
Addressed comments. |
vasild
left a comment
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.
Approach ACK 80f5c5442
Before this commit, CAddress disk serialization was messy. It stored
CLIENT_VERSION in the first 4 bytes, optionally OR'ed with ADDRV2_FORMAT.
- All bits except ADDRV2_FORMAT were ignored, making it hard to use for actual
future format changes.
- ADDRV2_FORMAT determines whether or not nServices is serialized in LE64
format or in CompactSize format.
- Whether or not the embedded CService is serialized in V1 or V2 format is
determined by the stream's version having ADDRV2_FORMAT (as opposed to the
nServices encoding, which is determined by the disk version).
To improve the situation, this commit introduces the following disk
serialization format, compatible with earlier versions, but better defined for
future changes:
- The first 4 bytes store a format version number. Its low 19 bits are ignored
(as it historically stored the CLIENT_VERSION), but its high 13 bits specify
the serialization exactly:
- 0x00000000: LE64 encoding for nServices, V1 encoding for CService
- 0x20000000: CompactSize encoding for nServices, V2 encoding for CService
- Any other value triggers an unsupported format error on deserialization,
and can be used for future format changes.
- The ADDRV2_FORMAT flag in the stream's version does not impact the actual
serialization format; it only determines whether V2 encoding is permitted;
whether it's actually enabled depends solely on the disk version number.
Operationally the changes to the deserializer are:
- Failure when the stored format version number is unexpected.
- The embedded CService's format is determined by the stored format version
number rather than the stream's version number.
These do no introduce incompatibilities, as no code versions exist that write
any value other than 0 or 0x20000000 in the top 13 bits, and no code paths
where the stream's version differs from the stored version.
|
Rebased, and addressed comments. |
vasild
left a comment
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.
ACK f8866e8
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.
ACK f8866e8 tested rebased to master and built/run/restarted with DEBUG_ADDRMAN, peers.dat and anchors ser/deser seems fine
hebasto
left a comment
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.
Approach ACK
|
@hebasto I think you need to leave a new review. |
hebasto
left a comment
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.
| uint32_t stored_format_version = DISK_VERSION_INIT; | ||
| if (s.GetVersion() & ADDRV2_FORMAT) stored_format_version |= DISK_VERSION_ADDRV2; | ||
| READWRITE(stored_format_version); | ||
| stored_format_version &= ~DISK_VERSION_IGNORE_MASK; // ignore low bits |
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:
This is the only place (besides two assertions above) where DISK_VERSION_IGNORE_MASK is used, and it is inverted. Isn't it more clear:
| stored_format_version &= ~DISK_VERSION_IGNORE_MASK; // ignore low bits | |
| stored_format_version &= DISK_VERSION_MASK; // ignore low bits |
?
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.
Will do if I retouch.
|
ACK f8866e8 |
|
Code review ACK f8866e8 |
…drv2 anchors.dat f8866e8 Add roundtrip fuzz tests for CAddress serialization (Pieter Wuille) e2f0548 Use addrv2 serialization in anchors.dat (Pieter Wuille) 8cd8f37 Introduce well-defined CAddress disk serialization (Pieter Wuille) Pull request description: Alternative to bitcoin#20509. This makes the `CAddress` disk serialization format well defined, and uses it to enable addrv2 support in anchors.dat (in a way that's compatible with older software). The new format is: - The first 4 bytes store a format version number. Its low 19 bits are ignored (as those historically stored the `CLIENT_VERSION`), but its high 13 bits specify the actual serialization: - 0x00000000: LE64 encoding for `nServices`, V1 encoding for `CService` (like pre-BIP155 network serialization). - 0x20000000: CompactSize encoding for `nServices`, V2 encoding for `CService` (like BIP155 network serialization). - Any other value triggers an unsupported format error on deserialization, and can be used for future format changes. - The `ADDRV2_FORMAT` flag in the stream's version does not determine the actual serialization format; it only sets whether or not V2 encoding is permitted. ACKs for top commit: achow101: ACK f8866e8 laanwj: Code review ACK f8866e8 vasild: ACK f8866e8 jonatack: ACK f8866e8 tested rebased to master and built/run/restarted with DEBUG_ADDRMAN, peers.dat and anchors ser/deser seems fine hebasto: ACK f8866e8, tested on Linux Mint 20.1 (x86_64). Tree-SHA512: 3898f8a8c51783a46dd0aae03fa10060521f5dd6e79315fe95ba807689e78f202388ffa28c40bf156c6f7b1fc2ce806b155dcbe56027df73d039a55331723796
|
review ACK f8866e8 🕑 Show signature and timestampSignature: Timestamp of file with hash |
| (void)mh.IsCommandValid(); | ||
| }) | ||
| FUZZ_TARGET_DESERIALIZE(address_deserialize, { | ||
| FUZZ_TARGET_DESERIALIZE(address_deserialize_v1_notime, { |
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.
Copied the fuzz inputs in commit bitcoin-core/qa-assets@836513a, so that the targets have something nice to start with.
Alternative to #20509.
This makes the
CAddressdisk serialization format well defined, and uses it to enable addrv2 support in anchors.dat (in a way that's compatible with older software). The new format is:CLIENT_VERSION), but its high 13 bits specify the actual serialization:nServices, V1 encoding forCService(like pre-BIP155 network serialization).nServices, V2 encoding forCService(like BIP155 network serialization).ADDRV2_FORMATflag in the stream's version does not determine the actual serialization format; it only sets whether or not V2 encoding is permitted.