Completed
Push — master ( 31933a...221a1f )
by thomas
20:56
created

Hasher::calculate()   A

Complexity

Conditions 4
Paths 4

Size

Total Lines 17
Code Lines 10

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 9
CRAP Score 4.016

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 4
eloc 10
nc 4
nop 3
dl 0
loc 17
ccs 9
cts 10
cp 0.9
crap 4.016
rs 9.2
c 1
b 0
f 0
1
<?php
2
3
namespace BitWasp\Bitcoin\Transaction\SignatureHash;
4
5
use BitWasp\Bitcoin\Bitcoin;
6
use BitWasp\Bitcoin\Crypto\Hash;
7
use BitWasp\Bitcoin\Script\ScriptInterface;
8
use BitWasp\Bitcoin\Serializer\Transaction\TransactionSerializer;
9
use BitWasp\Bitcoin\Serializer\Transaction\TransactionSerializerInterface;
10
use BitWasp\Bitcoin\Transaction\TransactionInterface;
11
use BitWasp\Buffertools\Buffer;
12
use BitWasp\Buffertools\BufferInterface;
13
14
class Hasher extends SigHash
15
{
16
    /**
17
     * @var TransactionSerializerInterface
18
     */
19
    private $txSerializer;
20
21
    /**
22
     * Hasher constructor.
23
     * @param TransactionInterface $transaction
24
     * @param TransactionSerializerInterface|null $txSerializer
25
     */
26 86
    public function __construct(TransactionInterface $transaction, TransactionSerializerInterface $txSerializer = null)
27
    {
28 86
        $this->txSerializer = $txSerializer ?: new TransactionSerializer();
29 86
        parent::__construct($transaction);
30 86
    }
31
32
    /**
33
     * Calculate the hash of the current transaction, when you are looking to
34
     * spend $txOut, and are signing $inputToSign. The SigHashType defaults to
35
     * SIGHASH_ALL, though SIGHASH_SINGLE, SIGHASH_NONE, SIGHASH_ANYONECANPAY
36
     * can be used.
37
     *
38
     * @param ScriptInterface $txOutScript
39
     * @param int $inputToSign
40
     * @param int $sighashType
41
     * @return BufferInterface
42
     * @throws \Exception
43
     */
44 86
    public function calculate(ScriptInterface $txOutScript, $inputToSign, $sighashType = SigHash::ALL)
45
    {
46 86
        $math = Bitcoin::getMath();
47 86
        if ($inputToSign >= count($this->tx->getInputs())) {
48
            return Buffer::hex('0100000000000000000000000000000000000000000000000000000000000000', 32, $math);
49
        }
50
51 86
        if (($sighashType & 0x1f) == SigHash::SINGLE) {
52 8
            if ($inputToSign >= count($this->tx->getOutputs())) {
53 2
                return Buffer::hex('0100000000000000000000000000000000000000000000000000000000000000', 32, $math);
54
            }
55
        }
56
57 86
        $serializer = new TxSigHashSerializer($this->tx, $txOutScript, $inputToSign, $sighashType);
58 86
        $sigHashData = new Buffer($serializer->serializeTransaction() . pack('V', $sighashType));
59 86
        return Hash::sha256d($sigHashData);
60
    }
61
}
62