chain: Better ReadState

This commit is contained in:
Łukasz Magiera 2019-08-16 04:33:59 +02:00
parent 6bee253e33
commit 3327781e60
2 changed files with 33 additions and 8 deletions

View File

@ -2,6 +2,7 @@ package vm
import (
"fmt"
"golang.org/x/xerrors"
"reflect"
actors "github.com/filecoin-project/go-lotus/chain/actors"
@ -13,6 +14,7 @@ import (
type invoker struct {
builtInCode map[cid.Cid]nativeCode
builtInState map[cid.Cid]reflect.Type
}
type invokeFunc func(act *types.Actor, vmctx types.VMContext, params []byte) ([]byte, aerrors.ActorError)
@ -21,14 +23,15 @@ type nativeCode []invokeFunc
func newInvoker() *invoker {
inv := &invoker{
builtInCode: make(map[cid.Cid]nativeCode),
builtInState: make(map[cid.Cid]reflect.Type),
}
// add builtInCode using: register(cid, singleton)
inv.register(actors.InitActorCodeCid, actors.InitActor{})
inv.register(actors.StorageMarketActorCodeCid, actors.StorageMarketActor{})
inv.register(actors.StorageMinerCodeCid, actors.StorageMinerActor{})
inv.register(actors.MultisigActorCodeCid, actors.MultiSigActor{})
inv.register(actors.PaymentChannelActorCodeCid, actors.PaymentChannelActor{})
inv.register(actors.InitActorCodeCid, actors.InitActor{}, actors.InitActorState{})
inv.register(actors.StorageMarketActorCodeCid, actors.StorageMarketActor{}, actors.StorageMarketState{})
inv.register(actors.StorageMinerCodeCid, actors.StorageMinerActor{}, actors.StorageMinerActorState{})
inv.register(actors.MultisigActorCodeCid, actors.MultiSigActor{}, actors.MultiSigActorState{})
inv.register(actors.PaymentChannelActorCodeCid, actors.PaymentChannelActor{}, actors.PaymentChannelActorState{})
return inv
}
@ -46,12 +49,13 @@ func (inv *invoker) Invoke(act *types.Actor, vmctx types.VMContext, method uint6
}
func (inv *invoker) register(c cid.Cid, instance Invokee) {
func (inv *invoker) register(c cid.Cid, instance Invokee, state interface{}) {
code, err := inv.transform(instance)
if err != nil {
panic(err)
}
inv.builtInCode[c] = code
inv.builtInState[c] = reflect.TypeOf(state)
}
type Invokee interface {
@ -136,3 +140,19 @@ func (*invoker) transform(instance Invokee) (nativeCode, error) {
}
return code, nil
}
func DumpActorState(code cid.Cid, b []byte) (interface{}, error) {
i := newInvoker() // TODO: register builtins in init block
typ, ok := i.builtInState[code]
if !ok {
return nil, xerrors.New("state type for actor not found")
}
rv := reflect.New(typ)
if err := cbor.DecodeInto(b, rv.Interface()); err != nil {
return nil, err
}
return rv.Elem().Interface(), nil
}

View File

@ -244,8 +244,13 @@ func (a *FullNodeAPI) ChainReadState(ctx context.Context, act *types.Actor, ts *
return nil, err
}
var oif interface{}
if err := state.Store.Get(context.TODO(), act.Head, &oif); err != nil {
blk, err := state.Store.Blocks.GetBlock(ctx, act.Head)
if err != nil {
return nil, err
}
oif, err := vm.DumpActorState(act.Code, blk.RawData())
if err != nil {
return nil, err
}