github.com/turingchain2020/turingchain@v1.1.21/system/dapp/register.go (about)

     1  // Copyright Turing Corp. 2018 All Rights Reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package dapp
     6  
     7  //store package store the world - state data
     8  import (
     9  	"github.com/turingchain2020/turingchain/client"
    10  	"github.com/turingchain2020/turingchain/common/address"
    11  	log "github.com/turingchain2020/turingchain/common/log/log15"
    12  	"github.com/turingchain2020/turingchain/types"
    13  )
    14  
    15  var elog = log.New("module", "execs")
    16  
    17  // DriverCreate defines a drivercreate function
    18  type DriverCreate func() Driver
    19  
    20  type driverWithHeight struct {
    21  	create DriverCreate
    22  	height int64
    23  }
    24  
    25  var (
    26  	execDrivers        = make(map[string]*driverWithHeight)
    27  	execAddressNameMap = make(map[string]string)
    28  	registedExecDriver = make(map[string]*driverWithHeight)
    29  )
    30  
    31  // Register register dcriver height in name
    32  func Register(cfg *types.TuringchainConfig, name string, create DriverCreate, height int64) {
    33  	if cfg == nil {
    34  		panic("Execute: GetConfig is nil")
    35  	}
    36  	if create == nil {
    37  		panic("Execute: Register driver is nil")
    38  	}
    39  	if _, dup := registedExecDriver[name]; dup {
    40  		panic("Execute: Register called twice for driver " + name)
    41  	}
    42  	driverHeight := &driverWithHeight{
    43  		create: create,
    44  		height: height,
    45  	}
    46  	registedExecDriver[name] = driverHeight
    47  	//考虑到前期平行链兼容性和防止误操作(平行链下转账到一个主链合约),也会注册主链合约(不带前缀)的地址
    48  	registerAddress(name)
    49  	execDrivers[ExecAddress(name)] = driverHeight
    50  	if cfg.IsPara() {
    51  		paraHeight := cfg.GetFork("ForkEnableParaRegExec")
    52  		if paraHeight < height {
    53  			paraHeight = height
    54  		}
    55  		//平行链的合约地址是通过user.p.x.name计算的
    56  		paraDriverName := cfg.ExecName(name)
    57  		registerAddress(paraDriverName)
    58  		execDrivers[ExecAddress(paraDriverName)] = &driverWithHeight{
    59  			create: create,
    60  			height: paraHeight,
    61  		}
    62  	}
    63  }
    64  
    65  // LoadDriver load driver
    66  func LoadDriver(name string, height int64) (driver Driver, err error) {
    67  	// user.evm.xxxx 的交易,使用evm执行器
    68  	//   user.p.evm
    69  	name = string(types.GetRealExecName([]byte(name)))
    70  	c, ok := registedExecDriver[name]
    71  	if !ok {
    72  		elog.Debug("LoadDriver", "driver", name)
    73  		return nil, types.ErrUnRegistedDriver
    74  	}
    75  	if height >= c.height || height == -1 {
    76  		return c.create(), nil
    77  	}
    78  	return nil, types.ErrUnknowDriver
    79  }
    80  
    81  //LoadDriverWithClient load
    82  func LoadDriverWithClient(qclent client.QueueProtocolAPI, name string, height int64) (driver Driver, err error) {
    83  	driver, err = LoadDriver(name, height)
    84  	if err != nil {
    85  		return nil, err
    86  	}
    87  	driver.SetAPI(qclent)
    88  	return driver, nil
    89  }
    90  
    91  // LoadDriverAllow load driver allow
    92  func LoadDriverAllow(qclent client.QueueProtocolAPI, tx *types.Transaction, index int, height int64) (driver Driver) {
    93  	exec, err := LoadDriverWithClient(qclent, string(tx.Execer), height)
    94  	if err == nil {
    95  		exec.SetEnv(height, 0, 0)
    96  		err = exec.Allow(tx, index)
    97  	}
    98  	if err != nil {
    99  		exec, err = LoadDriverWithClient(qclent, "none", height)
   100  		if err != nil {
   101  			panic(err)
   102  		}
   103  	} else {
   104  		exec.SetName(string(types.GetRealExecName(tx.Execer)))
   105  		exec.SetCurrentExecName(string(tx.Execer))
   106  	}
   107  	return exec
   108  }
   109  
   110  // IsDriverAddress whether or not execdrivers by address
   111  func IsDriverAddress(addr string, height int64) bool {
   112  	c, ok := execDrivers[addr]
   113  	if !ok {
   114  		return false
   115  	}
   116  	if height >= c.height || height == -1 {
   117  		return true
   118  	}
   119  	return false
   120  }
   121  
   122  func registerAddress(name string) {
   123  	if len(name) == 0 {
   124  		panic("empty name string")
   125  	}
   126  	addr := ExecAddress(name)
   127  	execAddressNameMap[name] = addr
   128  }
   129  
   130  // ExecAddress return exec address
   131  func ExecAddress(name string) string {
   132  	if addr, ok := execAddressNameMap[name]; ok {
   133  		return addr
   134  	}
   135  	return address.ExecAddress(name)
   136  }