Skip to content
This repository has been archived by the owner on Jun 17, 2020. It is now read-only.

Commit

Permalink
Handle all unexpected cases of bad genesis tx output sums
Browse files Browse the repository at this point in the history
Reformat exception messages for more clarity.

Also rename availableInputValue variable to remainingInputValue for clarity of its purpose.

Update the tests to conform to this more strict logic, and add new test cases for "tx outputs
too low / high" case.
  • Loading branch information
chirhonul committed Aug 10, 2018
1 parent 3703ecf commit 317a0ce
Show file tree
Hide file tree
Showing 2 changed files with 88 additions and 13 deletions.
15 changes: 9 additions & 6 deletions src/main/java/bisq/core/dao/node/parser/GenesisTxParser.java
Original file line number Diff line number Diff line change
Expand Up @@ -41,19 +41,22 @@ public static Optional<Tx> findGenesisTx(String genesisTxId, int genesisBlockHei

TempTx tempTx = TempTx.fromRawTx(rawTx);
tempTx.setTxType(TxType.GENESIS);
long availableInputValue = genesisTotalSupply.getValue();
long remainingInputValue = genesisTotalSupply.getValue();
for (int i = 0; i < tempTx.getTempTxOutputs().size(); ++i) {
TempTxOutput txOutput = tempTx.getTempTxOutputs().get(i);
long value = txOutput.getValue();
boolean isValid = value <= availableInputValue;
boolean isValid = value <= remainingInputValue;
if (!isValid)
throw new InvalidGenesisTxException("Genesis tx is isValid. " +
"availableInputValue=" + availableInputValue + "; txOutput=" + txOutput.toString());
throw new InvalidGenesisTxException("Genesis tx is invalid; using more than available inputs. " +
"Remaining input value is " + remainingInputValue + " sat; tx info: " + tempTx.toString());

availableInputValue -= value;
remainingInputValue -= value;
txOutput.setTxOutputType(TxOutputType.GENESIS_OUTPUT);
}

if (remainingInputValue > 0) {
throw new InvalidGenesisTxException("Genesis tx is invalid; not using all available inputs. " +
"Remaining input value is " + remainingInputValue + " sat, tx info: " + tempTx.toString());
}
return Optional.of(Tx.fromTempTx(tempTx));
}
}
86 changes: 79 additions & 7 deletions src/test/java/bisq/core/dao/node/parser/GenesisTxParserTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

package bisq.core.dao.node.parser;

import bisq.core.dao.node.parser.exceptions.InvalidGenesisTxException;
import bisq.core.dao.state.blockchain.RawTx;
import bisq.core.dao.state.blockchain.RawTxOutput;
import bisq.core.dao.state.blockchain.TempTx;
Expand Down Expand Up @@ -49,14 +50,22 @@ public void testGetGenesisTx() {
new TxInput("tx0", 0, null),
new TxInput("tx1", 1, null)
);
final List<RawTxOutput> outputs = Arrays.asList(new RawTxOutput(0, 101, null, null, null, null, blockHeight));
RawTxOutput output = new RawTxOutput(
0,
genesisTotalSupply.value,
null,
null,
null,
null,
blockHeight
);
RawTx rawTx = new RawTx(
"tx2",
blockHeight,
blockHash,
time,
ImmutableList.copyOf(inputs),
ImmutableList.copyOf(outputs)
ImmutableList.copyOf(Arrays.asList(output))
);

String genesisTxId = "genesisTxId";
Expand All @@ -75,7 +84,7 @@ public void testGetGenesisTx() {
blockHash,
time,
ImmutableList.copyOf(inputs),
ImmutableList.copyOf(outputs)
ImmutableList.copyOf(Arrays.asList(output))
);
result = GenesisTxParser.findGenesisTx(genesisTxId, genesisBlockHeight, genesisTotalSupply, rawTx);
want = Optional.empty();
Expand All @@ -88,7 +97,7 @@ public void testGetGenesisTx() {
blockHash,
time,
ImmutableList.copyOf(inputs),
ImmutableList.copyOf(outputs)
ImmutableList.copyOf(Arrays.asList(output))
);
result = GenesisTxParser.findGenesisTx(genesisTxId, genesisBlockHeight, genesisTotalSupply, rawTx);

Expand All @@ -99,9 +108,72 @@ public void testGetGenesisTx() {
}
Tx tx = Tx.fromTempTx(tempTx);
want = Optional.of(tx);

Assert.assertEquals(want, result);
// TODO(chirhonul): test that only outputs in tx summing exactly to genesisTotalSupply is accepted, and
// that code under test raises RuntimeError otherwise.

// With correct tx id and block height, but too low sum of outputs (lower than genesisTotalSupply), we
// should see an exception raised.
output = new RawTxOutput(
0,
genesisTotalSupply.value - 1,
null,
null,
null,
null,
blockHeight
);
rawTx = new RawTx(
genesisTxId,
blockHeight,
blockHash,
time,
ImmutableList.copyOf(inputs),
ImmutableList.copyOf(Arrays.asList(output))
);
try {
result = GenesisTxParser.findGenesisTx(genesisTxId, genesisBlockHeight, genesisTotalSupply, rawTx);
Assert.fail("Expected an InvalidGenesisTxException to be thrown when outputs are too low");
} catch (InvalidGenesisTxException igtxe) {
String wantMessage = "Genesis tx is invalid; not using all available inputs. Remaining input value is 1 sat";
Assert.assertTrue("Unexpected exception, want message starting with " +
"'" + wantMessage + "', got '" + igtxe.getMessage() + "'", igtxe.getMessage().startsWith(wantMessage));
}

// With correct tx id and block height, but too high sum of outputs (higher than from genesisTotalSupply), we
// should see an exception raised.
RawTxOutput output1 = new RawTxOutput(
0,
genesisTotalSupply.value - 2,
null,
null,
null,
null,
blockHeight
);
RawTxOutput output2 = new RawTxOutput(
0,
3,
null,
null,
null,
null,
blockHeight
);
rawTx = new RawTx(
genesisTxId,
blockHeight,
blockHash,
time,
ImmutableList.copyOf(inputs),
ImmutableList.copyOf(Arrays.asList(output1, output2))
);
try {
result = GenesisTxParser.findGenesisTx(genesisTxId, genesisBlockHeight, genesisTotalSupply, rawTx);
Assert.fail("Expected an InvalidGenesisTxException to be thrown when outputs are too high");
} catch (InvalidGenesisTxException igtxe) {
String wantMessage = "Genesis tx is invalid; using more than available inputs. Remaining input value is 2 sat";
Assert.assertTrue("Unexpected exception, want message starting with " +
"'" + wantMessage + "', got '" + igtxe.getMessage() + "'", igtxe.getMessage().startsWith(wantMessage));
}

}
}

0 comments on commit 317a0ce

Please sign in to comment.