gcs: add witness stack items to filter, update tests
This commit is contained in:
parent
c01c00e8b4
commit
b3d8578868
2 changed files with 61 additions and 8 deletions
|
@ -194,6 +194,16 @@ func (b *GCSBuilder) AddScript(script []byte) *GCSBuilder {
|
||||||
return b.AddEntries(data)
|
return b.AddEntries(data)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AddWitness adds each item of the passed filter stack to the filer.
|
||||||
|
func (b *GCSBuilder) AddWitness(witness wire.TxWitness) *GCSBuilder {
|
||||||
|
// Do nothing if the builder's already errored out.
|
||||||
|
if b.err != nil {
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
|
||||||
|
return b.AddEntries(witness)
|
||||||
|
}
|
||||||
|
|
||||||
// Build returns a function which builds a GCS filter with the given parameters
|
// Build returns a function which builds a GCS filter with the given parameters
|
||||||
// and data.
|
// and data.
|
||||||
func (b *GCSBuilder) Build() (*gcs.Filter, error) {
|
func (b *GCSBuilder) Build() (*gcs.Filter, error) {
|
||||||
|
@ -318,19 +328,36 @@ func BuildBasicFilter(block *wire.MsgBlock) (*gcs.Filter, error) {
|
||||||
func BuildExtFilter(block *wire.MsgBlock) (*gcs.Filter, error) {
|
func BuildExtFilter(block *wire.MsgBlock) (*gcs.Filter, error) {
|
||||||
blockHash := block.BlockHash()
|
blockHash := block.BlockHash()
|
||||||
b := WithKeyHash(&blockHash)
|
b := WithKeyHash(&blockHash)
|
||||||
|
|
||||||
|
// If the filter had an issue with the specified key, then we force it
|
||||||
|
// to bubble up here by calling the Key() function.
|
||||||
_, err := b.Key()
|
_, err := b.Key()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// In order to build an extended filter, we add the hash of each
|
||||||
|
// transaction as well as each piece of witness data included in both
|
||||||
|
// the sigScript and the witness stack of an input.
|
||||||
for i, tx := range block.Transactions {
|
for i, tx := range block.Transactions {
|
||||||
|
// First we'll compute the bash of the transaction and add that
|
||||||
|
// directly to the filter.
|
||||||
txHash := tx.TxHash()
|
txHash := tx.TxHash()
|
||||||
b.AddHash(&txHash)
|
b.AddHash(&txHash)
|
||||||
|
|
||||||
// Skip the inputs for the coinbase transaction
|
// Skip the inputs for the coinbase transaction
|
||||||
if i != 0 {
|
if i != 0 {
|
||||||
|
// Next, for each input, we'll add the sigScript (if
|
||||||
|
// it's present), and also the witness stack (if it's
|
||||||
|
// present)
|
||||||
for _, txIn := range tx.TxIn {
|
for _, txIn := range tx.TxIn {
|
||||||
if txIn.SignatureScript != nil {
|
if txIn.SignatureScript != nil {
|
||||||
b.AddScript(txIn.SignatureScript)
|
b.AddScript(txIn.SignatureScript)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if len(txIn.Witness) != 0 {
|
||||||
|
b.AddWitness(txIn.Witness)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -49,6 +49,20 @@ var (
|
||||||
testHash = "000000000000000000496d7ff9bd2c96154a8d64260e8b3b411e625712abb14c"
|
testHash = "000000000000000000496d7ff9bd2c96154a8d64260e8b3b411e625712abb14c"
|
||||||
|
|
||||||
testAddr = "3Nxwenay9Z8Lc9JBiywExpnEFiLp6Afp8v"
|
testAddr = "3Nxwenay9Z8Lc9JBiywExpnEFiLp6Afp8v"
|
||||||
|
|
||||||
|
witness = [][]byte{
|
||||||
|
[]byte{0x4c, 0xb1, 0xab, 0x12, 0x57, 0x62, 0x1e, 0x41,
|
||||||
|
0x3b, 0x8b, 0x0e, 0x26, 0x64, 0x8d, 0x4a, 0x15,
|
||||||
|
0x3b, 0x8b, 0x0e, 0x26, 0x64, 0x8d, 0x4a, 0x15,
|
||||||
|
0x3b, 0x8b, 0x0e, 0x26, 0x64, 0x8d, 0x4a, 0x15},
|
||||||
|
|
||||||
|
[]byte{0xdd, 0xa3, 0x5a, 0x14, 0x88, 0xfb, 0x97, 0xb6,
|
||||||
|
0xeb, 0x3f, 0xe6, 0xe9, 0xef, 0x2a, 0x25, 0x81,
|
||||||
|
0x4e, 0x39, 0x6f, 0xb5, 0xdc, 0x29, 0x5f, 0xe9,
|
||||||
|
0x94, 0xb9, 0x67, 0x89, 0xb2, 0x1a, 0x03, 0x98,
|
||||||
|
0x94, 0xb9, 0x67, 0x89, 0xb2, 0x1a, 0x03, 0x98,
|
||||||
|
0x94, 0xb9, 0x67, 0x89, 0xb2, 0x1a, 0x03, 0x98},
|
||||||
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
// TestUseBlockHash tests using a block hash as a filter key.
|
// TestUseBlockHash tests using a block hash as a filter key.
|
||||||
|
@ -88,11 +102,11 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
hex.EncodeToString(key[:]),
|
hex.EncodeToString(key[:]),
|
||||||
hex.EncodeToString(testKey[:]))
|
hex.EncodeToString(testKey[:]))
|
||||||
}
|
}
|
||||||
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, t)
|
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a key hash and non-default P and test it.
|
// Create a GCSBuilder with a key hash and non-default P and test it.
|
||||||
b = builder.WithKeyHashP(hash, 30)
|
b = builder.WithKeyHashP(hash, 30)
|
||||||
BuilderTest(b, hash, 30, outPoint, addrBytes, t)
|
BuilderTest(b, hash, 30, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a random key, set the key from a hash
|
// Create a GCSBuilder with a random key, set the key from a hash
|
||||||
// manually, check that the key is correct, and test it.
|
// manually, check that the key is correct, and test it.
|
||||||
|
@ -108,7 +122,7 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
hex.EncodeToString(key[:]),
|
hex.EncodeToString(key[:]),
|
||||||
hex.EncodeToString(testKey[:]))
|
hex.EncodeToString(testKey[:]))
|
||||||
}
|
}
|
||||||
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, t)
|
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a random key and test it.
|
// Create a GCSBuilder with a random key and test it.
|
||||||
b = builder.WithRandomKey()
|
b = builder.WithRandomKey()
|
||||||
|
@ -118,7 +132,7 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
err.Error())
|
err.Error())
|
||||||
}
|
}
|
||||||
t.Logf("Random Key 1: %s", hex.EncodeToString(key1[:]))
|
t.Logf("Random Key 1: %s", hex.EncodeToString(key1[:]))
|
||||||
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, t)
|
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a random key and non-default P and test it.
|
// Create a GCSBuilder with a random key and non-default P and test it.
|
||||||
b = builder.WithRandomKeyP(30)
|
b = builder.WithRandomKeyP(30)
|
||||||
|
@ -131,7 +145,7 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
if key2 == key1 {
|
if key2 == key1 {
|
||||||
t.Fatalf("Random keys are the same!")
|
t.Fatalf("Random keys are the same!")
|
||||||
}
|
}
|
||||||
BuilderTest(b, hash, 30, outPoint, addrBytes, t)
|
BuilderTest(b, hash, 30, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a known key and test it.
|
// Create a GCSBuilder with a known key and test it.
|
||||||
b = builder.WithKey(testKey)
|
b = builder.WithKey(testKey)
|
||||||
|
@ -145,7 +159,7 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
hex.EncodeToString(key[:]),
|
hex.EncodeToString(key[:]),
|
||||||
hex.EncodeToString(testKey[:]))
|
hex.EncodeToString(testKey[:]))
|
||||||
}
|
}
|
||||||
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, t)
|
BuilderTest(b, hash, builder.DefaultP, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a known key and non-default P and test it.
|
// Create a GCSBuilder with a known key and non-default P and test it.
|
||||||
b = builder.WithKeyP(testKey, 30)
|
b = builder.WithKeyP(testKey, 30)
|
||||||
|
@ -159,7 +173,7 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
hex.EncodeToString(key[:]),
|
hex.EncodeToString(key[:]),
|
||||||
hex.EncodeToString(testKey[:]))
|
hex.EncodeToString(testKey[:]))
|
||||||
}
|
}
|
||||||
BuilderTest(b, hash, 30, outPoint, addrBytes, t)
|
BuilderTest(b, hash, 30, outPoint, addrBytes, witness, t)
|
||||||
|
|
||||||
// Create a GCSBuilder with a known key and too-high P and ensure error
|
// Create a GCSBuilder with a known key and too-high P and ensure error
|
||||||
// works throughout all functions that use it.
|
// works throughout all functions that use it.
|
||||||
|
@ -177,7 +191,9 @@ func TestUseBlockHash(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func BuilderTest(b *builder.GCSBuilder, hash *chainhash.Hash, p uint8,
|
func BuilderTest(b *builder.GCSBuilder, hash *chainhash.Hash, p uint8,
|
||||||
outPoint wire.OutPoint, addrBytes []byte, t *testing.T) {
|
outPoint wire.OutPoint, addrBytes []byte, witness wire.TxWitness,
|
||||||
|
t *testing.T) {
|
||||||
|
|
||||||
key, err := b.Key()
|
key, err := b.Key()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("Builder instantiation with key hash failed: %s",
|
t.Fatalf("Builder instantiation with key hash failed: %s",
|
||||||
|
@ -256,4 +272,14 @@ func BuilderTest(b *builder.GCSBuilder, hash *chainhash.Hash, p uint8,
|
||||||
t.Logf("Filter didn't match when it should have!")
|
t.Logf("Filter didn't match when it should have!")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Add a routine witness stack, build a filter, and test that it
|
||||||
|
// matches.
|
||||||
|
b.AddWitness(witness)
|
||||||
|
match, err = f.MatchAny(key, witness)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("Filter match any failed: %s", err)
|
||||||
|
}
|
||||||
|
if !match {
|
||||||
|
t.Logf("Filter didn't match when it should have!")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue