mirror of
https://github.com/lightningnetwork/lnd.git
synced 2025-10-10 14:52:54 +02:00
input: add new ScriptIsOpReturn helper func
This commit is contained in:
51
input/fuzz_script_is_op_return_test.go
Normal file
51
input/fuzz_script_is_op_return_test.go
Normal file
@@ -0,0 +1,51 @@
|
|||||||
|
package input
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/btcsuite/btcd/chaincfg"
|
||||||
|
"github.com/btcsuite/btcd/txscript"
|
||||||
|
"github.com/stretchr/testify/require"
|
||||||
|
)
|
||||||
|
|
||||||
|
// FuzzScriptIsOpReturn fuzzes the ScriptIsOpReturn function.
|
||||||
|
func FuzzScriptIsOpReturn(f *testing.F) {
|
||||||
|
// Seed the corpus with some representative inputs.
|
||||||
|
f.Add([]byte{})
|
||||||
|
f.Add([]byte{txscript.OP_RETURN})
|
||||||
|
|
||||||
|
// Use our canonical ScriptBuilder to produce a valid OP_RETURN script.
|
||||||
|
builder := txscript.NewScriptBuilder()
|
||||||
|
builder.AddOp(txscript.OP_RETURN)
|
||||||
|
builder.AddData([]byte("valid data"))
|
||||||
|
script, err := builder.Script()
|
||||||
|
require.NoError(f, err)
|
||||||
|
f.Add(script)
|
||||||
|
|
||||||
|
// An example of a script that does not start with OP_RETURN.
|
||||||
|
f.Add([]byte{txscript.OP_DUP, txscript.OP_RETURN})
|
||||||
|
|
||||||
|
f.Fuzz(func(t *testing.T, pkScript []byte) {
|
||||||
|
result := ScriptIsOpReturn(pkScript)
|
||||||
|
|
||||||
|
var expected bool
|
||||||
|
if len(script) == 0 || script[0] != txscript.OP_RETURN {
|
||||||
|
expected = false
|
||||||
|
} else {
|
||||||
|
scriptClass, _, _, err := txscript.ExtractPkScriptAddrs(
|
||||||
|
pkScript, &chaincfg.MainNetParams,
|
||||||
|
)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("unable to extract pk script "+
|
||||||
|
"addresses: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
expected = scriptClass == txscript.NullDataTy
|
||||||
|
}
|
||||||
|
|
||||||
|
if result != expected {
|
||||||
|
t.Fatalf("for script %x, expected ScriptIsOpReturn=%v;"+
|
||||||
|
" got %v", script, expected, result)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
@@ -3239,3 +3239,36 @@ func ComputeCommitmentPoint(commitSecret []byte) *btcec.PublicKey {
|
|||||||
_, pubKey := btcec.PrivKeyFromBytes(commitSecret)
|
_, pubKey := btcec.PrivKeyFromBytes(commitSecret)
|
||||||
return pubKey
|
return pubKey
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ScriptIsOpReturn returns true if the passed script is an OP_RETURN script.
|
||||||
|
//
|
||||||
|
// Lifted from the txscript package:
|
||||||
|
// https://github.com/btcsuite/btcd/blob/cc26860b40265e1332cca8748c5dbaf3c81cc094/txscript/standard.go#L493-L526.
|
||||||
|
//
|
||||||
|
//nolint:ll
|
||||||
|
func ScriptIsOpReturn(script []byte) bool {
|
||||||
|
// A null script is of the form:
|
||||||
|
// OP_RETURN <optional data>
|
||||||
|
//
|
||||||
|
// Thus, it can either be a single OP_RETURN or an OP_RETURN followed by
|
||||||
|
// a data push up to MaxDataCarrierSize bytes.
|
||||||
|
|
||||||
|
// The script can't possibly be a null data script if it doesn't start
|
||||||
|
// with OP_RETURN. Fail fast to avoid more work below.
|
||||||
|
if len(script) < 1 || script[0] != txscript.OP_RETURN {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// Single OP_RETURN.
|
||||||
|
if len(script) == 1 {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// OP_RETURN followed by data push up to MaxDataCarrierSize bytes.
|
||||||
|
tokenizer := txscript.MakeScriptTokenizer(0, script[1:])
|
||||||
|
|
||||||
|
return tokenizer.Next() && tokenizer.Done() &&
|
||||||
|
(txscript.IsSmallInt(tokenizer.Opcode()) ||
|
||||||
|
tokenizer.Opcode() <= txscript.OP_PUSHDATA4) &&
|
||||||
|
len(tokenizer.Data()) <= txscript.MaxDataCarrierSize
|
||||||
|
}
|
||||||
|
Reference in New Issue
Block a user