Vulnerability: Recommendation: Remove TxFinalizationModel and TxFinalizationVerifier. Implement stronger checks in Merkle
Severity: medium

Description:
`TxFinalizationVerifier` is an abstraction around the block inclusion check needed for many of the features of plasma exit games. It uses a struct defined in `TxFinalizationModel` as inputs to its two functions: `isStandardFinalized` and `isProtocolFinalized`.\\n`isStandardFinalized` returns the result of an inclusion proof. Although there are several branches, only the first is used:\\n```\\n/\\*\\*\\n\\* @notice Checks whether a transaction is "standard finalized"\\n\\* @dev MVP: requires that both inclusion proof and confirm signature is checked\\n\\* @dev MoreVp: checks inclusion proof only\\n\\*/\\nfunction isStandardFinalized(Model.Data memory data) public view returns (bool) {\\n    if (data.protocol == Protocol.MORE\\_VP()) {\\n        return checkInclusionProof(data);\\n    } else if (data.protocol == Protocol.MVP()) {\\n        revert("MVP is not yet supported");\\n    } else {\\n        revert("Invalid protocol value");\\n    }\\n}\\n```\\n\\n`isProtocolFinalized` is unused:\\n```\\n/\\*\\*\\n\\* @notice Checks whether a transaction is "protocol finalized"\\n\\* @dev MVP: must be standard finalized\\n\\* @dev MoreVp: allows in-flight tx, so only checks for the existence of the transaction\\n\\*/\\nfunction isProtocolFinalized(Model.Data memory data) public view returns (bool) {\\n    if (data.protocol == Protocol.MORE\\_VP()) {\\n        return data.txBytes.length > 0;\\n    } else if (data.protocol == Protocol.MVP()) {\\n        revert("MVP is not yet supported");\\n    } else {\\n        revert("Invalid protocol value");\\n    }\\n}\\n```\\n\\nThe abstraction used introduces branching logic and requires several files to be visited to fully understand the function of each line of code: `ITxFinalizationVerifier`, `TxFinalizationModel`, `TxPosLib`, `Protocol`, `BlockController`, and `Merkle`. Additionally, the abstraction obfuscates the underlying inclusion proof primitive when used in the exit game contracts. `isStandardFinalized` is not clearly an inclusion proof, and `isProtocolFinalized` simply adds confusion.\\n```\\nfunction checkInclusionProof(Model.Data memory data) private view returns (bool) {\\n    if (data.inclusionProof.length == 0) {\\n        return false;\\n    }\\n\\n    (bytes32 root,) = data.framework.blocks(data.txPos.blockNum());\\n    bytes32 leafData = keccak256(data.txBytes);\\n    return Merkle.checkMembership(\\n        leafData, data.txPos.txIndex(), root, data.inclusionProof\\n    );\\n}\\n```\\n\\nBy introducing the abstraction of `TxFinalizationVerifier`, the input validation performed by `Merkle` is split across multiple files, and the reasonable-seeming decision of calling `Merkle.checkMembership` directly becomes unsafe. In fact, this occurs in one location in the contracts:\\n```\\nfunction verifyAndDeterminePositionOfTransactionIncludedInBlock(\\n    bytes memory txbytes,\\n    UtxoPosLib.UtxoPos memory utxoPos,\\n    bytes32 root,\\n    bytes memory inclusionProof\\n)\\n    private\\n    pure\\n    returns(uint256)\\n{\\n    bytes32 leaf = keccak256(txbytes);\\n    require(\\n        Merkle.checkMembership(leaf, utxoPos.txIndex(), root, inclusionProof),\\n        "Transaction is not included in block of Plasma chain"\\n    );\\n\\n    return utxoPos.value;\\n}\\n```\\n

Impact:

Recommended mitigation:
PaymentChallengeIFEOutputSpent.verifyInFlightTransactionStandardFinalized:\\n```\\nrequire(controller.txFinalizationVerifier.isStandardFinalized(finalizationData), "In-flight transaction not finalized");\\n```\\n\\nPaymentChallengeIFENotCanonical.verifyCompetingTxFinalized:\\n```\\nrequire(self.txFinalizationVerifier.isStandardFinalized(finalizationData), "Failed to verify the position of competing tx");\\n```\\n\\nPaymentStartInFlightExit.verifyInputTransactionIsStandardFinalized:\\n```\\nrequire(exitData.controller.txFinalizationVerifier.isStandardFinalized(finalizationData),\\n        "Input transaction is not standard finalized");\\n```\\n\\nIf none of the above recommendations are implemented, ensure that `PaymentChallengeIFENotCanonical` uses the abstraction `TxFinalizationVerifier` so that a length check is performed on the inclusion proof.\\nCorresponding issue in plasma-contracts repo: https://github.com/omisego/plasma-contracts/issues/471