Bitcoin Time Locks | BitMEX Blog
Abstract: We examine the various time locks in Bitcoin, a feature which can ensure that a particular Bitcoin transaction is only valid until after a certain point in time, normally in the future. The report explains why the adoption of some of the time lock features are important from a mining incentivisation perspective and we argue that the current adoption rates are worryingly low.
Overview
In a few months time, by perhaps April 2024, the Bitcoin block subsidy is set to half to just 3.125 Bitcoin. Up until now, Bitcoin has relied on a significant block subsidy to keep the network secure. However, in our view, in the coming years Satoshi’s vision that “the incentive can transition entirely to transaction fees and be completely inflation free” will finally begin to be tested. There has been discussion about whether Bitcoin can achieve this and remain secure. For instance, if fee rates are high enough to secure the network, will that drive out certain popular use cases? Another consideration is what role will alternative use cases like Ordinals play in generating sustainable miner revenue? In this report we will focus on what we consider to be a critical component of transitioning incentives to fees, something often overlooked, Bitcoin’s time lock features.
Bitcoins Time Lock Features
Bitcoin has four categories of built in time lock features. These are mechanisms which ensure a Bitcoin transaction can only be included in the blockchain after a certain point in time or block height. There are various different types of time locks, which are outlined in the table below.
Name (Type) |
Date became effective |
Description |
Locktime (Absolute) |
This feature was available when Bitcoin launched in 2009 |
This is the most basic type of time lock and also the most common type, it is an absolute timelock. Bitcoin transactions have their own special field called a locktime. There are essentially three choices here:
The block height based locktime parameter can have a value of up to 500 million, therefore in around 9,500 years this feature may no longer work. While the time and date based approach may cease to function earlier, in the year 2106, due to the limits of using a 32 bit integer to display a time and date. |
nSequence (Relative) | July 2016 softfork | This is a relative locktime based feature. In contrast to the transaction level field above, this is an input level feature. Each Bitcoin transaction input has a special field called nSequence, which like locktime has been around since 2009. However, in a 2016 softfork (BIP68) this field was repurposed to mean relative locktime. Prior to this, the purpose of nSequence field appears to be an improperly implemented and unused early transaction replacement system. The field can also be used to disable or enable the above absolute locktime feature and flag for RBF. More concisely, if all the nSequence values are set to 0xFFFFFFFF, absolute locktime is disabled.
Relative locktime ensures a transaction input is invalid, for a specified period of time after the previous output has been confirmed. This is what makes this a relative timelock, rather than an absolute one. Although each transaction input has an nSequence field, relative locktime applies to the whole transaction. The relative locktime condition must be satisfied for all inputs for the transaction to be valid. Only part of the 32 bit field is used for relative locktime, due to the RBF flagging capabilities. Therefore, the nSequence field only has 16 bits to encode the time lock. 2^16 seconds is only 18 hours and 12 minutes, which was considered too short. Therefore, the time units used are batches of 512 seconds, allowing for a maximum relative lock of 388 days. |
OP_CHECKLOCKTIMEVERIFY (Absolute) |
December 2015 |
This transaction opcode (AKA OP_CLTV) essentially has the same functionality as locktime, which is an absolute time lock. This opcode ensures that the functionality can now be controlled at the script level, providing more flexibility and control. For instance the opcode can be combined with other conditions such as AND, IF and ELSE functions. |
OP_CHECKSEQUENCEVERIF Y (Relative) |
July 2016 (Same activation point as relative locktime) |
This opcode (AKA OP_CSV) essentially has the same functionality as the relative locktime. Again, as its an opcode, the functionality can now be controlled at the script level, providing more flexibility. This feature can be used to create multiple conflicting unconfirmed chains of transactions from the same output, such that certain paths have priority over others depending on the time periods. This is extensively used in lightning. |
The below example transaction structure shows that multiple types of time locks can be used in the same transaction and it also illustrates where in the transactions the time locks are located.
Illustration showing where the various locktime options can be included in a transaction
Source: BitMEX Research
In addition to the above, it should be noted that outputs to the coinbase transaction have a 100 block relative time lock period, which can be considered as another type of time lock.
Fee Sniping and Miner Incentives
When the block subsidy declines and incentives transition to fees, it is not only the fees associated with your incoming transitions which provide security. Security for confirmed transactions is also provided by transaction fees related to other transactions. If you are receiving a large Bitcoin payment, say worth $10 million, in an untrusted environment, the transaction fee associated with the transaction may not necessarily provide much security. After one confirmation, the sender could create a conflicting transaction with a higher fee, say a $500,000 fee and attempt a double spend. Some miners could then be tempted to re-org backwards one block, to obtain the higher fee.
Now of course miners don’t want to go backwards like this. Miners want to mine at the tip, because other miners choose to work on the most work chain and if a miner tries to go backwards, there is a higher probability their block goes stale and they earn nothing. On the other hand, if the incentive to re-org back one block is large enough, due to a large revenue difference between the tip and re-organising backwards, it is something nefarious miners could consider.
There are several characteristics which Bitcoin has that mitigate against this problem. Firstly, the block subsidy. With a large percentage of the miner incentives fixed, there is little incentive to re-org backwards in an attempt to scoop up more fees. As the block subsidy declines, another mechanism is supposed to prevent this attack, the so-called deep memory pool. This is the idea that Bitcoin blocks will always be full and there will be a permanent backlog of transactions in the memory pool and fees associated with these, which incentivise the miners to move the chain forwards. With a deep memory pool, there is always some revenue to be earned from mining at the tip. This idea was very controversial back in the blocksize war days, with larger blockers opposing full blocks and a deep memory pool. Whatever one thinks of the deep memory pool, locktime is important here. This deep memory pool security system works much better with people using locktime, when the locktime set by the sender is the prevailing block height.
In simplified terms, when the block subsidy is low, a nefarious miner considering a one block re-org backwards has different considerations depending on locktime usage. Without any locktime usage, the miner could look at all the transaction fees in the last block and all the transaction fees in the memory pool. The miner can then select the highest fee paying transactions from both buckets and construct the block. If the fee income here is much higher than the potential fee income from the new block mined at the tip, the miner could attempt a re-org backwards. On the other hand, if everyone used locktime, using the current block height, then for any new transactions in the memory pool, if the miner re-orgs backwards, they cannot obtain these fees. If the miner re-orgs backwards, they can only include some, but not all, of the highest fee rate transactions in the memory pool in their candidate block. Any new high fee transactions with locktime enabled, which get broadcast, encourage the miners to mine at the tip. Therefore the incentive to re-org backwards is reduced. In our view, this feature is critical to Bitcoin’s long term security.
Bitcoin Core Defaults
Since perhaps late 2014, transactions produced by the Bitcoin Core wallet have the locktime field set to the current block by default to prevent fee sniping. As the notes in Bitcoin Code’s codebase say:
For a large miner the value of the transactions in the best block and the mempool can exceed the cost of deliberately attempting to mine two blocks to orphan the current best block. By setting nLockTime such that only the next block can include the transaction, we discourage this practice as the height restricted and limited blocksize gives miners considering fee sniping fewer options for pulling off this attack. A simple way to think about this is from the wallet’s point of view we always want the blockchain to move forward. By setting nLockTime this way we’re basically making the statement that we only want this transaction to appear in the next block; we don’t want to potentially encourage reorgs by allowing transactions to appear at lower heights than the next block in forks of the best chain.
Source: https://github.com/bitcoin/bitcoin/blob/fb0ac482eee761ec17ed2c11df11e054347a026d/src/wallet/wallet.cpp#L2133
As far as we know, not many other wallets use locktime by default and most of the adoption is generated from people using Bitcoin Core. Therefore locktime usage is often seen as a proxy for the usage of Bitcoin Core’s wallet. It should be noted that the Electrum Bitcoin Wallet also sets the locktime as the latest block height.
Time Lock Adoption Data
We plan to provide more data and statistics on the usage of the various timelocks in the coming weeks. However, some charts related to time lock adoption are available on the https://transactionfee.info/ website.
Source: https://transactionfee.info/charts/transactions-height-based-locktime/
The data shows that adoption of block height based absolute timelocks picked up in early 2015, to around the 20% level. We believe the cause of this is that the Bitcoin Core wallet made absolute timelock the default policy in late 2014. Since then adoption has flatlined at around 20%, before declining to c10% in 2023. We believe this decline is due to the adoption of Ordinals and BRC 20 tokens. This new usage of the blockchain priced out some other users and as far as we know, Ordinals related transactions typically do not enable locktime by default.
Adoption of date based absolute locktimes is very low with only very niche usage. Before Ordinals, adoption peaked at around 0.1% of all Bitcoin transactions and post the Ordinals boom usage is around 0.05%.
Conclusion
One can think of the decision to add locktime to your transaction as a tragedy of the commons type problem. An individual user may just want their transaction confirmed no matter what, they may not care about the wider security benefits locktime provides to the Bitcoin network. On the other hand, the magnitude of this apparent game theory problem is small, because the cost of adding the locktime to your transaction is very low. Almost all users won’t be making this decision on a per transaction basis anyway and most users do not even know what locktime is. In most scenarios it will depend on the default policy of the wallet one is using.
We would argue that adoption of locktime is important to Bitcoin’s long term security and would encourage wallet developers to implement it. The current c20% adoption level feels quite low. Bitcoin advocates now potentially have another issue to preach about:
- Control your own private keys. Not your keys, not your coins! Sell the Blackrock ETF and buy real Bitcoin!
- Run your own node to fully validate incoming transactions
- Set locktime for your outgoing transactions and/or use wallets which add locktime by default.