6

I don't understand why I'm reading that after a hard fork, the existing transactions would be on both chains but the new transactions will only be on one or the other (resulting in 2 different chains, thus an altcoin). Won't even new transactions eventually end up on both chains?

Transactions don't care about block size, so both versions should accept them. Even if one chain has already included it, software for the 2nd chain won't care about the first chain, so the 2nd should still have those transactions in its pool, resulting in it being put into the 2nd chain as well.

I don't see how this will result in 2 separate chains... it seems like both chains will always have approximately the same exact transactions, just possibly in a different order and grouped into different blocks.

The only exception to this I can think of is if a double-spend is attempted. Then it's possible that one of the chains will accept one of the double-spend transactions and the other chain will accept the other.

But otherwise, I don't see how there would be a difference.

4

This actually happened on Ethereum when they had a hard fork. If a transaction is valid on both chains (spends outputs from before the fork), and gets propagated to both chains, then yes, there is no reason it won't be added to blocks on both chains.

However, there are still two chains. When the same transaction gets added to both chains, they are included in two separate blocks; one block from chain A and one block from chain B. The outputs of such transactions can only be spent on their corresponding chain, even though the transaction that created them was identical.

Lets say that we have a chain that hard forks at block height 100. We now have chain A and chain B. A transaction is created using UTXOs from the block at height 90, and propagates on both networks. Chain A includes it in its block at height 108, and chain B includes it in its block at height 110 (although it could just as well be 108 on its chain too). Now a new transaction is created spending a UTXO from the first transaction on chain A. That second transaction can only ever propagate on chain B if it exclusively spends from UTXOs on both chains. This becomes increasingly less likely over time.

Since most new transactions on a chain are only valid for that chain, it won't take long before the two chains have barely any transactions in common.

It's also important to note that bitcoin clients will drop connections to clients that propagate blocks from the other chain. This will help to segregate the network, and prevent transactions from propagating on both chains, even when they are valid on both. There could be malicious entities that "bridge" the two networks, looking for transactions that are valid on both, but there isn't any real incentive for that sort of misbehavior.

  • 2
    This is mostly right, however I believe you're mistaken in the third paragraph. A TXID is deterministically created from the transaction data. It is independent of the block in which it was included. Therefore, the outputs created by the same transaction on the two chains are identical even if the transaction is confirmed in a different block, and any followup transaction is valid on both chains. This is why you either have to doublespend or include funds that are only valid on one chain (e.g. mining reward or previously separated funds) to separate your funds respective to the two chains. – Murch Mar 21 '17 at 8:34
  • @Murch, yep, you are correct. I was thinking that TxIn's specify the block ID as well as the TXID. – Jestin Mar 21 '17 at 14:00
  • @Murch, updated the answer. – Jestin Mar 21 '17 at 14:07
  • @Murch Two follow-up questions: (1) How can I separate my funds on the 2 chains via double-spending? (2) How do separate my funds using "mining reward" transactions? I do not own any. – John Red Jun 11 '17 at 4:26
4

Let's diagram an example hard fork block chain:

A <-- B <-- C  <-- D   (current consensus rules chain, "original chain")       
      ^---- C' <-- D'  (new consensus rules chain, "new chain")

If you received a transaction output in block A or B, you could spend it on both the original chain and the new chain[*]. How that would work out depends a lot of whether the new chain includes replay protection.

Replay protection

The new chain may optionally require replay protection, which would most likely be a change in the data used to create the transaction signature. For example, normally a transaction signature signs a hash of the identifier of the inputs being spent as well as all of the outputs; for a hard fork, this could be changed to require the signature hash additionally include the value "Hard Fork #123". This would have the following results:

  1. The old chain wouldn't accept any transactions made for the new chain because it wouldn't attempt to calculate the signature hash with the extra "Hard Fork #123" data, so all signatures made for the new chain would look invalid to it.

  2. The new chain wouldn't accept any transactions made for the old chain because they'd be missing the required "Hard Fork #123" data.

For most (probably all) wallets, adding "Hard Fork #123" to the data used to create the signature hash would be technically easy---but it does require the wallet author support the fork and that all users upgrade before the fork. More difficult (depending on the wallet) would be supporting both signature formats and perhaps allowing the user to choose between them. Still, I'd imagine it's not too hard.

However, most proposed hard forks for Bitcoin don't include this or any other direct replay protection. This is probably because their proposers think there will be a lower chance of adoption if developers and users have to take any action to use the hard fork.

Interestingly, the original 0.1 version of the Bitcoin protocol included three opcodes (OP_VER, OP_VERIF, and OP_VERNOTIF) that could be used for replay protection during a hard fork by allowing you to specify what rules had to be followed to spend your transaction on different VERsions of the protocol.

Unfortunately, the design didn't work and Satoshi Nakamoto removed the opcodes from the protocol. In addition to providing replay protection after a hard fork, they could be used to cause a type of hard fork called a consensus failure. (And, if you're following along with current drama, it has not escaped the amusement of some people that Bitcoin's earliest protocol allowed a hard fork be triggered by a VER.)

Incompatible transactions

So if replay protection is available, you could spend an output from either block A or block B on either chain, but you'd have to sign the transaction differently for each chain---ensuring that you could send funds on the original chain to Alice and the funds on the new chain to Bob.

Without replay protection, you have to send the funds on both chains at the same time because whatever transaction you create will be valid on both chains[*]. However, there are ways to create transactions that will only be valid on one chain even if replay protection isn't available---they're just harder:

  • Using coinbase coins: blocks C (original chain) and C' (new chain) have different coinbase transactions. (A coinbase transaction is the special transaction in a block that pays the miner for creating that block.) These transactions are only valid on their particular chain, and any transactions that descend from them are also only valid on their particular chain.

    So if you're a miner or you know a miner, you just have to mix at least 1 satoshi from them with your spend from block A and your transaction will have ad hoc replay protection.

    However, there's two problems with this: (1) you need to know a miner who's willing to help you out and (2) coinbase transactions aren't spendable for 100 blocks[*], so you'd have to wait for a while after the hard fork before you could start spending.

  • Conflicting transactions: if you create two different transactions and send them to the two different block chains, it's possible (but not guaranteed) that one transaction will be confirmed in block C and one transaction in block C'.

    As long as blocks C and C' remain part of their respective block chains then any transactions that spend your transaction can only be part of their respective block chains.

    Since there's no guarantee that you can split coins this way, it's usually a good idea to send both separate transactions to yourself so that there's no way you can lose money beyond the transaction fees. Also, there's a way to increase your chances of the coins being split:

    • On the chain with the highest block height, spend your coins to yourself using nLockTime to target the current block height.

    • When the transaction above confirms, spend your coins to yourself on the other chain with no nLockTime.

     

    Assuming the different chains have even a modest difference in height, this works because your nLockTime transaction is only initially valid on the higher-height chain, so it can't immediately be added to the lower-height chain. (Credit: I first heard of a method like this from Peter Todd; I don't know if he originated it, nor if this is exactly the method he was thinking about---I had to guess at how it would work from him just saying "use nLockTime".)

A warning

Hard forks, especially those without replay protection, break many normal assumptions of Bitcoin wallets. As such, there's a significant risk that you will lose money if you spend or accept bitcoins during an ongoing hard fork. Please be careful.


[*] Hard forks can change any part of the system, so the generalizations made in this post may not apply to all cases. However, I've tried to make them applicable to most proposed hard forks that only change a few things, such as the perpetually-debated maximum block size/weight.

  • If you don't know how to create a nLockTime transaction, you could just spend the money to yourself on the chain with the lower fees, and then doublespend it with a higher fee on the other chain. – Murch Mar 21 '17 at 21:08
  • Yep, that would probably work too. Although the nLockTime trick is pretty easy if you use Bitcoin Core since its anti-fee sniping protection causes it to nLockTime's all of its transactions to the current block height by default. :-) (Seriously, all wallets should be doing that.) – David A. Harding Mar 21 '17 at 23:03
  • Yeah, but if you are using another wallet, it may not be as simple. ;) – Murch Mar 21 '17 at 23:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.