OSDN Git Service

feat(bcrp): implement IsBCRPScript func and unit test (#1857)
authorDeKaiju <longjinglv@gmail.com>
Tue, 6 Apr 2021 09:27:57 +0000 (17:27 +0800)
committerGitHub <noreply@github.com>
Tue, 6 Apr 2021 09:27:57 +0000 (17:27 +0800)
consensus/segwit/segwit.go
consensus/segwit/segwit_test.go

index b85c4e8..6f70d2c 100644 (file)
@@ -1,6 +1,7 @@
 package segwit
 
 import (
+       "bytes"
        "errors"
 
        "github.com/bytom/bytom/consensus"
@@ -8,6 +9,9 @@ import (
        "github.com/bytom/bytom/protocol/vm/vmutil"
 )
 
+//bcrp bytom contract register protocol
+const bcrp = "bcrp"
+
 func IsP2WScript(prog []byte) bool {
        return IsP2WPKHScript(prog) || IsP2WSHScript(prog) || IsStraightforward(prog)
 }
@@ -51,6 +55,46 @@ func IsP2WSHScript(prog []byte) bool {
        return insts[1].Op == vm.OP_DATA_32 && len(insts[1].Data) == consensus.PayToWitnessScriptHashDataSize
 }
 
+// IsBCRPScript checks if a control program is bytom contract register protocol
+// BCRP script format: OP_FAIL + OP_PUSHDATA1 + "04" + hex("bcrp") + OP_PUSHDATA1 + "01" + "01" + OP_PUSHDATA1 + len(contract) + contract
+func IsBCRPScript(prog []byte) bool {
+       inst, err := vm.ParseProgram(prog)
+       if err != nil {
+               return false
+       }
+
+       if len(inst) != 4 {
+               return false
+       }
+
+       if inst[0].Op != vm.OP_FAIL {
+               return false
+       }
+
+       if inst[1].Op != vm.OP_PUSHDATA1 {
+               return false
+       }
+
+       if !bytes.Equal(inst[1].Data, []byte(bcrp)) {
+               return false
+       }
+
+       if inst[2].Op != vm.OP_PUSHDATA1 {
+               return false
+       }
+
+       // version 1
+       if !bytes.Equal(inst[2].Data, []byte{byte(1)}) {
+               return false
+       }
+
+       if inst[3].Op != vm.OP_PUSHDATA1 {
+               return false
+       }
+
+       return true
+}
+
 func ConvertP2PKHSigProgram(prog []byte) ([]byte, error) {
        insts, err := vm.ParseProgram(prog)
        if err != nil {
index 14ec13b..dfc7cd8 100644 (file)
@@ -119,3 +119,47 @@ func TestProgramType(t *testing.T) {
                }
        }
 }
+
+func TestIsBCRPScript(t *testing.T) {
+       tests := []struct {
+               program  string
+               expected bool
+       }{
+               {
+                       program:  "",
+                       expected: false,
+               },
+               {
+                       program:  "ae20ac20f5cdb9ada2ae9836bcfff32126d6b885aa3f73ee111a95d1bf37f3904aca5151ad",
+                       expected: false,
+               },
+               {
+                       program:  "694c04626372704c01014c2820e9108d3ca8049800727f6a3505b3a2710dc579405dde03c250f16d9a7e1e6e787403ae7cac00c0",
+                       expected: false,
+               },
+               {
+                       program:  "6a4c04424352504c01014c2820e9108d3ca8049800727f6a3505b3a2710dc579405dde03c250f16d9a7e1e6e787403ae7cac00c0",
+                       expected: false,
+               },
+               {
+                       program:  "6a4c04626372704c01024c2820e9108d3ca8049800727f6a3505b3a2710dc579405dde03c250f16d9a7e1e6e787403ae7cac00c0",
+                       expected: false,
+               },
+               {
+                       program:  "6a4c04626372704c01014c2820e9108d3ca8049800727f6a3505b3a2710dc579405dde03c250f16d9a7e1e6e787403ae7cac00c0",
+                       expected: true,
+               },
+       }
+
+       for i, test := range tests {
+               program, err := hex.DecodeString(test.program)
+               if err != nil {
+                       t.Fatal(err)
+               }
+
+               expected := IsBCRPScript(program)
+               if expected != test.expected {
+                       t.Errorf("TestIsTemplateRegister #%d failed: got %v want %v", i, expected, test.expected)
+               }
+       }
+}