Fix issuanceVerification in parser

This commit is contained in:
Manfred Karrer 2017-05-10 21:18:32 +02:00
parent 82b1400681
commit b31f8ea243
9 changed files with 37 additions and 28 deletions

View File

@ -18,8 +18,8 @@
package io.bisq.core.dao;
public class DaoConstants {
public static final byte OP_RETURN_TYPE_COMPENSATION_REQUEST = (byte) 0x01;
public static final byte OP_RETURN_TYPE_VOTE = (byte) 0x02;
public static final byte OP_RETURN_TYPE_LOCK_UP = (byte) 0x03;
public static final byte OP_RETURN_TYPE_UNLOCK = (byte) 0x04;
}

View File

@ -27,7 +27,9 @@ public enum JsonTxType {
PAY_TRADE_FEE("Pay trade fee"),
COMPENSATION_REQUEST("Compensation request"),
VOTE("Vote"),
ISSUANCE("Issuance");
ISSUANCE("Issuance"),
LOCK_UP("Lockup"),
UN_LOCK("Unlock");
@Getter
private String displayString;

View File

@ -289,6 +289,7 @@ public class BsqParser {
// We use order of output index. An output is a BSQ utxo as long there is enough input value
final List<TxOutput> outputs = tx.getOutputs();
TxOutput btcOutput = null;
TxOutput bsqOutput = null;
for (int index = 0; index < outputs.size(); index++) {
TxOutput txOutput = outputs.get(index);
final long txOutputValue = txOutput.getValue();
@ -300,17 +301,13 @@ public class BsqParser {
bsqChainState.addUnspentTxOutput(txOutput);
tx.setTxType(TxType.TRANSFER_BSQ);
txOutput.setTxOutputType(TxOutputType.BSQ_OUTPUT);
bsqOutput = txOutput;
availableValue -= txOutputValue;
if (availableValue == 0) {
log.debug("We don't have anymore BSQ to spend");
}
} else if (issuanceVerification.maybeProcessData(tx, index)) {
// it is not a BSQ or OP_RETURN output
// check is we have a sponsor tx
log.debug("We got a issuance tx and process the data");
break;
} else if (opReturnVerification.maybeProcessOpReturnData(tx, index, availableValue, blockHeight, btcOutput)) {
} else if (opReturnVerification.maybeProcessOpReturnData(tx, index, availableValue, blockHeight, btcOutput, bsqOutput)) {
log.debug("We processed valid DAO OP_RETURN data");
} else {
btcOutput = txOutput;
@ -329,6 +326,9 @@ public class BsqParser {
if (tx.getTxType() == null)
tx.setTxType(TxType.PAY_TRADE_FEE);
}
} else if (issuanceVerification.maybeProcessData(tx)) {
// We don't have any BSQ input, so we test if it is a sponsor/issuance tx
log.debug("We got a issuance tx and process the data");
}
return isBsqTx;

View File

@ -35,6 +35,7 @@ public class CompensationRequestVerification {
boolean maybeProcessData(Tx tx, byte[] opReturnData, TxOutput opReturnTxOutput, long fee, int blockHeight, TxOutput btcTxOutput) {
if (btcTxOutput != null &&
opReturnData.length == 2 &&
Version.COMPENSATION_REQUEST_VERSION == opReturnData[1] &&
fee == bsqChainState.getCreateCompensationRequestFee(blockHeight) &&
bsqChainState.isCompensationRequestPeriodValid(blockHeight)) {

View File

@ -51,12 +51,13 @@ public class IssuanceVerification {
this.compensationRequestModel = compensationRequestModel;
}
boolean maybeProcessData(Tx tx, int outputIndex) {
boolean maybeProcessData(Tx tx) {
List<TxOutput> outputs = tx.getOutputs();
if (outputIndex == 0 && outputs.size() >= 2) {
TxOutput btcTxOutput = outputs.get(0);
TxOutput bsqTxOutput = outputs.get(1);
if (outputs.size() >= 2) {
TxOutput bsqTxOutput = outputs.get(0);
TxOutput btcTxOutput = outputs.get(1);
final String btcAddress = btcTxOutput.getAddress();
// TODO find address by block range/cycle
final Optional<CompensationRequest> compensationRequest = compensationRequestModel.findByAddress(btcAddress);
if (compensationRequest.isPresent()) {
final CompensationRequest compensationRequest1 = compensationRequest.get();

View File

@ -40,7 +40,7 @@ public class OpReturnVerification {
}
boolean maybeProcessOpReturnData(Tx tx, int index, long availableValue,
int blockHeight, TxOutput btcOutput) {
int blockHeight, TxOutput btcOutput, TxOutput bsqOutput) {
List<TxOutput> txOutputs = tx.getOutputs();
TxOutput txOutput = txOutputs.get(index);
final long txOutputValue = txOutput.getValue();
@ -55,7 +55,7 @@ public class OpReturnVerification {
return compensationRequestVerification.maybeProcessData(tx, opReturnData, txOutput,
availableValue, blockHeight, btcOutput);
case DaoConstants.OP_RETURN_TYPE_VOTE:
return votingVerification.maybeProcessData(tx, opReturnData, txOutput, availableValue, blockHeight);
return votingVerification.maybeProcessData(tx, opReturnData, txOutput, availableValue, blockHeight, bsqOutput);
default:
log.warn("OP_RETURN data version does not match expected version bytes. opReturnData={}",
Utils.HEX.encode(opReturnData));

View File

@ -47,17 +47,20 @@ public class VotingVerification {
return false;
}
boolean maybeProcessData(Tx tx, byte[] opReturnData, TxOutput txOutput, long fee, int blockHeight) {
final int sizeOfCompRequestsVotes = (int) opReturnData[22];
if (Version.VOTING_VERSION == opReturnData[1] &&
sizeOfCompRequestsVotes % 2 == 0 &&
(opReturnData.length - 1) % 2 == 0 &&
opReturnData.length >= 23 + sizeOfCompRequestsVotes * 2 &&
fee == bsqChainState.getVotingFee(blockHeight) &&
bsqChainState.isVotingPeriodValid(blockHeight)) {
txOutput.setTxOutputType(TxOutputType.VOTING_OP_RETURN_OUTPUT);
tx.setTxType(TxType.VOTE);
return true;
boolean maybeProcessData(Tx tx, byte[] opReturnData, TxOutput txOutput, long fee, int blockHeight, TxOutput bsqOutput) {
if (Version.VOTING_VERSION == opReturnData[1] && opReturnData.length > 22) {
final int sizeOfCompRequestsVotes = (int) opReturnData[22];
if (bsqOutput != null &&
sizeOfCompRequestsVotes % 2 == 0 &&
opReturnData.length % 2 == 1 &&
opReturnData.length >= 23 + sizeOfCompRequestsVotes * 2 &&
fee == bsqChainState.getVotingFee(blockHeight) &&
bsqChainState.isVotingPeriodValid(blockHeight)) {
txOutput.setTxOutputType(TxOutputType.VOTING_OP_RETURN_OUTPUT);
tx.setTxType(TxType.VOTE);
// TODO use bsqOutput as weight
return true;
}
}
return false;
}

View File

@ -25,5 +25,7 @@ public enum TxType {
PAY_TRADE_FEE,
COMPENSATION_REQUEST,
VOTE,
ISSUANCE
ISSUANCE,
LOCK_UP,
UN_LOCK
}

View File

@ -175,7 +175,7 @@ public class Connection implements MessageListener {
// API
///////////////////////////////////////////////////////////////////////////////////////////
// Called form various threads
// Called from various threads
public void sendMessage(Msg msg) {
if (!stopped) {