github.com/MetalBlockchain/metalgo@v1.11.9/vms/rpcchainvm/factory.go (about) 1 // Copyright (C) 2019-2024, Ava Labs, Inc. All rights reserved. 2 // See the file LICENSE for licensing terms. 3 4 package rpcchainvm 5 6 import ( 7 "context" 8 "fmt" 9 10 "github.com/MetalBlockchain/metalgo/utils/logging" 11 "github.com/MetalBlockchain/metalgo/utils/resource" 12 "github.com/MetalBlockchain/metalgo/vms" 13 "github.com/MetalBlockchain/metalgo/vms/rpcchainvm/grpcutils" 14 "github.com/MetalBlockchain/metalgo/vms/rpcchainvm/runtime" 15 "github.com/MetalBlockchain/metalgo/vms/rpcchainvm/runtime/subprocess" 16 ) 17 18 var _ vms.Factory = (*factory)(nil) 19 20 type factory struct { 21 path string 22 processTracker resource.ProcessTracker 23 runtimeTracker runtime.Tracker 24 } 25 26 func NewFactory(path string, processTracker resource.ProcessTracker, runtimeTracker runtime.Tracker) vms.Factory { 27 return &factory{ 28 path: path, 29 processTracker: processTracker, 30 runtimeTracker: runtimeTracker, 31 } 32 } 33 34 func (f *factory) New(log logging.Logger) (interface{}, error) { 35 config := &subprocess.Config{ 36 Stderr: log, 37 Stdout: log, 38 HandshakeTimeout: runtime.DefaultHandshakeTimeout, 39 Log: log, 40 } 41 42 listener, err := grpcutils.NewListener() 43 if err != nil { 44 return nil, fmt.Errorf("failed to create listener: %w", err) 45 } 46 47 status, stopper, err := subprocess.Bootstrap( 48 context.TODO(), 49 listener, 50 subprocess.NewCmd(f.path), 51 config, 52 ) 53 if err != nil { 54 return nil, err 55 } 56 57 clientConn, err := grpcutils.Dial(status.Addr) 58 if err != nil { 59 return nil, err 60 } 61 62 vm := NewClient(clientConn) 63 vm.SetProcess(stopper, status.Pid, f.processTracker) 64 65 f.runtimeTracker.TrackRuntime(stopper) 66 67 return vm, nil 68 }