Skip to content

Conversation

@darosior
Copy link
Member

@darosior darosior commented Nov 22, 2019

This changes the current feerate computation from using virtual bytes to weight units for transaction size.

The transaction size being stored and used as virtual bytes introduced some non-negligible rounding and approximations (See #13283 for an example.). This patch set is an attempt to switch to using weight units in place of virtual bytes internally for a more accurate feerate computation, while leaving intact the vbyte interface.

There is, I think, a big cleanup needed (for example renaming feerate constants as xx_FEERATE would really improve readability) but I wanted to keep changes as minimal as possible.

Fixes #13283.

@DrahtBot
Copy link
Contributor

DrahtBot commented Nov 22, 2019

The following sections might be updated with supplementary metadata relevant to reviewers and maintainers.

Conflicts

Reviewers, 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.

@darosior darosior force-pushed the feerate_in_weight branch 3 times, most recently from faa72fe to 2542ca1 Compare November 25, 2019 20:57
@darosior
Copy link
Member Author

Rebased now that appveyor seems to be fixed.

@darosior darosior force-pushed the feerate_in_weight branch 2 times, most recently from 720da2e to dfa7655 Compare November 26, 2019 10:43
@darosior
Copy link
Member Author

darosior commented Dec 2, 2019

This might be "too late" but the fee estimation can be floored to 253 sat/kWU, so that the wallet doesn't create transaction below old feerate until most of the network relay 250 sat/kWU txs..

@darosior darosior force-pushed the feerate_in_weight branch 2 times, most recently from 732a5a7 to 5817a3e Compare December 4, 2019 11:21
@darosior
Copy link
Member Author

darosior commented Dec 4, 2019

Rebased.

@jb55
Copy link
Contributor

jb55 commented Dec 5, 2019

I can't help but wonder if there's a better abstraction here instead of random conversions happening everywhere...

@darosior
Copy link
Member Author

darosior commented Dec 9, 2019

I can't help but wonder if there's a better abstraction here instead of random conversions happening everywhere...

Conversion is needed anyway for every user input (and even for JSONRPC outputs) to not break the API..

@jb55
Copy link
Contributor

jb55 commented Dec 11, 2019 via email

Since Segregated Witness activation and the transaction size being determined in
wieght units, our internal logic for transaction size (and thus feerates) has relied
on virtual bytes.
Virtual bytes are useful for non-technical end-user experience, but can cause some issues
if the whole logic rely on this raw division.

For instance, if stored as an integer, the transaction size will be truncated, which can
lead to wrong feerate calculation. In order to patch this, GetVirtualTransactionSize()
rounds up.
This led to not only protecting the users from paying too-low fees and seeing their
transaction rejected, but this also implicitly increased the minimum feerate for
relaying transactions. For instance a minrelayfee(rate) of 1000sat/kvbyte is of 253sat/kWU,
while we could expect it to be 250sat/perkWU (see issue # 13283).

Using constants in weight units will allow us to avoid raw roundings for feerate computation
and to get an accurate feerate estimation (and a deterministic relay policy), while keeping
the cosiness of vbytes for non-technical end-users.
This adds transaction size utils in weight where there were only virtual
byte ones. This will allow to use weight units for feerate computation
later on while keeping accurate vbyte computation for not breaking the
API.
@darosior
Copy link
Member Author

Rebased.

Will rework the approach and include remarks from jb55 if there are some acks on the general concept of using / exposing weight units..

Most constants are unchanged but timed by 4 at initialization, mainly to avoid a big diff by rewriting all 'GetArg's because we need to still expose parameters as taking vbytes.
This adds weight units counter to the 'CTxMemPoolModifiedEntry' struct
to make weights the packages size unit.

This also treats block min feerate as per weight units, while leaving
intact the vbyte shroud for the user.
The functional tests in wallet_basic.py are also modified to check feerates
using weight units, as we don't round up anymore for transaction size computation.
@DrahtBot
Copy link
Contributor

Needs rebase

@ariard
Copy link

ariard commented Jun 22, 2020

Concept ACK.

Correctness of fee computation is safety-critical for any time-sensitive protocol like LN. Overpaying by default isn't the solution as you may have to save value for period of congestion. With this regards easing implementation of segwit fee-estimators should be highly considered.

As Rusty points out in related issue, this should be part of a wider discussion on a stable API for protocol applications on top of Bitcoin Core.

@darosior
Copy link
Member Author

darosior commented Jun 22, 2020 via email

@adamjonas
Copy link
Member

I gathered some opinions on this from a long time contributor about the concept, he replied:
"seems like a fine thing to do. also seems like not a high priority"

After looking at the code, however, his reaction was that the patch was too big for the benefit. Putting more data in the CTxMemPoolEntry especially stood out as an issue.

@darosior I think it's worth getting more conceptual review before you put in more effort. I believe it's clear that more discussions need to happen around ways to improve the linkages between Bitcoin Core and LN, but based on the opinions I gathered, the approach on this PR could use some more feedback.

@darosior
Copy link
Member Author

darosior commented Aug 14, 2020

@adamjonas this PR is a bad approach. It's been known and discussed above, so I don't think it's worth discussing it any more. However for the sake of the argument: I locally have a version which is an about 3x smaller diff, and regarding adding a field to the CTxMempoolEntry it's necessary anyway as to use weight-mesured feerates we need to track, well, the weight of the tx.

I agree it needs more conceptual feedback, but i don't want to ask for it before this patchset is reworked (will push soon ™️ ) as i think the boutique approach here could degrade the conceptual review.

Nonetheless, thank you for your interest.

@jnewbery
Copy link
Contributor

This has required rebase since February, and there are still conceptual questions outstanding. I'm going to close it for now.

@darosior - feel free to reopen (or open another PR) if you have something that's ready for review/discussion.

@jnewbery jnewbery closed this Sep 29, 2020
@bitcoin bitcoin locked as resolved and limited conversation to collaborators Feb 15, 2022
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.

minRelayTxFee should be calculated on weight, not vbytes. aka "vbytes must die"

7 participants