Skip to content
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

Use 2 hour grace period for key timestamps in importmulti rescans #9761

Merged
merged 4 commits into from
Feb 17, 2017

Conversation

ryanofsky
Copy link
Contributor

@gmaxwell pointed out the lack of grace period in #9490 (comment).

The importwallet RPC which uses key timestamps in a similar way already has a 2 hour grace period.

@gmaxwell
Copy link
Contributor

So one consequence of this is that if you use the manual pruning you will potentially prune past the time your imports will attempt to search, and then fail.

@laanwj
Copy link
Member

laanwj commented Feb 15, 2017

Concept ACK.

So one consequence of this is that if you use the manual pruning you will potentially prune past the time your imports will attempt to search, and then fail.

Yes. Though I'm not sure that warrants any changes. After all it's the same for importwallet already.

At the least this grace period needs to be clearly documented in the RPC help so that it can be taken into account.

@@ -1072,7 +1072,7 @@ UniValue importmulti(const JSONRPCRequest& mainRequest)
}

if (fRescan && fRunScan && requests.size() && nLowestTimestamp <= chainActive.Tip()->GetBlockTimeMax()) {
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(nLowestTimestamp) : chainActive.Genesis();
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(nLowestTimestamp - 7200) : chainActive.Genesis();
Copy link
Contributor

Choose a reason for hiding this comment

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

I think this works fine, but does it seem slightly safer to not allow it to go negative?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Added max call.

@ryanofsky
Copy link
Contributor Author

ryanofsky commented Feb 15, 2017

So one consequence of this is that if you use the manual pruning you will potentially prune past the time your imports will attempt to search, and then fail.

Yes. Though I'm not sure that warrants any changes. After all it's the same for importwallet already.

I would want to address this by only adding the grace period when fPruneMode is false. The way I see it, if you're using the rescan feature on a pruned node, you already have to be pretty careful, and while there are real improvements we can make for pruned nodes (like marking keys that could have incomplete transaction lists, or looking for spendable outputs in the utxo set in #9137), adding a grace period for importmulti rescans on pruned nodes is only a slightly useful thing to begin with, so it would be simplest for the code and for users to just keep the current behavior in this case.

At the least this grace period needs to be clearly documented in the RPC help so that it can be taken into account.

Will add a short note.

This change was discussed some on IRC:
https://botbot.me/freenode/bitcoin-core-dev/msg/80989053/
https://botbot.me/freenode/bitcoin-core-dev/msg/81013278/

@ryanofsky
Copy link
Contributor Author

ryanofsky commented Feb 15, 2017

Created #9773 to deal with the issue of pruned nodes. morcos argued against removing the grace period when fPruneMode was false because not having a grace period could potentially lead to missing transaction data, and gmaxwell argued against disabling importmulti rescans on pruned nodes because partial rescanning is an important feature for pruned nodes, so #9773 deals with the issue by returning errors from importmulti when rescans fail because blocks are missing or corrupt.

Still need to add some documentation about the grace period, and add a min call to avoid passing negative values to FindEarliestAtLeast, but the bulk of the code in this PR (i.e. import-rescan.py) is ready for review.

@laanwj
Copy link
Member

laanwj commented Feb 16, 2017

Making the grace period depend on whether the node is pruning or not sounds like a terrible idea to me. It ties together two different options in a completely unexpected way, that's just asking for people to make mistakes.

@gmaxwell
Copy link
Contributor

The whole reason manual pruning takes a timestamp is so harmonize it with this, so you can not prune what you need to import. I think this could be addressed by also adding an identical grace to the manual pruning time.

Get rid of partial functions so the test can be more easily extended to add
more variants of imports with options that affect rescanning (e.g. different
key timestamps).

Also change the second half of the test to send /to/ the imported addresses,
instead of /from/ the imported addresses. The goal of this part of the test was
to confirm that the wallet would pick up new transactions after an import
regardless of whether or not a rescan happened during the import. But because
the wallet can only do this reliably for incoming transactions and not outgoing
transactions (which require the wallet to look up transaction inputs) the test
previously was less meaningful than it should have been.
Gregory Maxwell <greg@xiph.org> pointed out the lack of grace period in
bitcoin#9490 (comment).

The importwallet RPC which uses key timestamps in a similar way already has a 2
hour grace period.
Copy link
Contributor Author

@ryanofsky ryanofsky left a comment

Choose a reason for hiding this comment

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

Added max call and updated RPC help text.

@@ -1072,7 +1072,7 @@ UniValue importmulti(const JSONRPCRequest& mainRequest)
}

if (fRescan && fRunScan && requests.size() && nLowestTimestamp <= chainActive.Tip()->GetBlockTimeMax()) {
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(nLowestTimestamp) : chainActive.Genesis();
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(nLowestTimestamp - 7200) : chainActive.Genesis();
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Added max call.

@morcos
Copy link
Contributor

morcos commented Feb 16, 2017

utACK e662af3

Please tag 0.14
only reviewed code changes did not review test changes

@@ -1072,7 +1073,7 @@ UniValue importmulti(const JSONRPCRequest& mainRequest)
}

if (fRescan && fRunScan && requests.size() && nLowestTimestamp <= chainActive.Tip()->GetBlockTimeMax()) {
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(nLowestTimestamp) : chainActive.Genesis();
CBlockIndex* pindex = nLowestTimestamp > minimumTimestamp ? chainActive.FindEarliestAtLeast(std::max<int64_t>(nLowestTimestamp - 7200, 0)) : chainActive.Genesis();
Copy link
Member

Choose a reason for hiding this comment

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

nit: I think this should be std::max<int64_t>(nLowestTimestamp - 7200, minimumTimestamp)

I only mention because I'm unsure if 0 has a special meaning somewhere.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

0 has special meaning for the CWallet::nTimeFirstKey variable, but I recently removed all outside references to that variable and made it private so that no other code that wasn't dealing with it directly would have to worry about special meanings of 0.

minimumTimestamp would work fine if it were set to 0 instead of 1, and I have some local changes to remove this variable, so I didn't want to add another use here.

Copy link
Member

Choose a reason for hiding this comment

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

Sounds good.

@laanwj laanwj added this to the 0.14.0 milestone Feb 16, 2017
@jtimon
Copy link
Contributor

jtimon commented Feb 16, 2017

Concept ACK, although as commented in #9778, if these grace periods need to be consistent, I think we should have a constant (also used for normal rescan?).

@laanwj
Copy link
Member

laanwj commented Feb 17, 2017

Concept ACK, although as commented in #9778, if these grace periods need to be consistent, I think we should have a constant (also used for normal rescan?).

Yes, would make sense to define a constant. No, that does not need to hold up merging this.

@laanwj laanwj merged commit e662af3 into bitcoin:master Feb 17, 2017
laanwj added a commit that referenced this pull request Feb 17, 2017
…i rescans

e662af3 Use 2 hour grace period for key timestamps in importmulti rescans (Russell Yanofsky)
38d3e9e [qa] Extend import-rescan.py to test imports on pruned nodes. (Russell Yanofsky)
c28583d [qa] Extend import-rescan.py to test specific key timestamps (Russell Yanofsky)
8be0866 [qa] Simplify import-rescan.py (Russell Yanofsky)
codablock pushed a commit to codablock/dash that referenced this pull request Feb 1, 2018
…ortmulti rescans

e662af3 Use 2 hour grace period for key timestamps in importmulti rescans (Russell Yanofsky)
38d3e9e [qa] Extend import-rescan.py to test imports on pruned nodes. (Russell Yanofsky)
c28583d [qa] Extend import-rescan.py to test specific key timestamps (Russell Yanofsky)
8be0866 [qa] Simplify import-rescan.py (Russell Yanofsky)
andvgal pushed a commit to energicryptocurrency/gen2-energi that referenced this pull request Jan 6, 2019
…ortmulti rescans

e662af3 Use 2 hour grace period for key timestamps in importmulti rescans (Russell Yanofsky)
38d3e9e [qa] Extend import-rescan.py to test imports on pruned nodes. (Russell Yanofsky)
c28583d [qa] Extend import-rescan.py to test specific key timestamps (Russell Yanofsky)
8be0866 [qa] Simplify import-rescan.py (Russell Yanofsky)
CryptoCentric pushed a commit to absolute-community/absolute that referenced this pull request Feb 28, 2019
…ortmulti rescans

e662af3 Use 2 hour grace period for key timestamps in importmulti rescans (Russell Yanofsky)
38d3e9e [qa] Extend import-rescan.py to test imports on pruned nodes. (Russell Yanofsky)
c28583d [qa] Extend import-rescan.py to test specific key timestamps (Russell Yanofsky)
8be0866 [qa] Simplify import-rescan.py (Russell Yanofsky)
CryptoCentric pushed a commit to absolute-community/absolute that referenced this pull request Mar 2, 2019
…ortmulti rescans

e662af3 Use 2 hour grace period for key timestamps in importmulti rescans (Russell Yanofsky)
38d3e9e [qa] Extend import-rescan.py to test imports on pruned nodes. (Russell Yanofsky)
c28583d [qa] Extend import-rescan.py to test specific key timestamps (Russell Yanofsky)
8be0866 [qa] Simplify import-rescan.py (Russell Yanofsky)
@bitcoin bitcoin locked as resolved and limited conversation to collaborators Sep 8, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants