From 372cba1fcac9f6de638c6b73c3f981685d6ddf34 Mon Sep 17 00:00:00 2001 From: Leonard Lyubich Date: Wed, 19 May 2021 15:28:10 +0300 Subject: [PATCH] [#505] ir/container: Check key ownership during set eACL handling Use NeoFS ID contract client to check if public key from notification event is tied to the owner of the container for which the eACL is being changed. Approve changes coming from the owner of the container only. Signed-off-by: Leonard Lyubich --- .../processors/container/process_eacl.go | 36 +++++++++++++++++-- .../processors/container/processor.go | 2 ++ 2 files changed, 36 insertions(+), 2 deletions(-) diff --git a/pkg/innerring/processors/container/process_eacl.go b/pkg/innerring/processors/container/process_eacl.go index 105553483a..b5b2e5509b 100644 --- a/pkg/innerring/processors/container/process_eacl.go +++ b/pkg/innerring/processors/container/process_eacl.go @@ -7,6 +7,7 @@ import ( "fmt" "github.com/nspcc-dev/neo-go/pkg/crypto/keys" + "github.com/nspcc-dev/neofs-api-go/pkg/acl/eacl" "github.com/nspcc-dev/neofs-node/pkg/morph/event/container" "go.uber.org/zap" ) @@ -43,9 +44,40 @@ func (cp *Processor) checkSetEACL(e container.SetEACL) error { return errors.New("invalid signature") } - // TODO: check key ownership + // verify the identity of the container owner + return cp.checkEACLOwnership(table, key) +} - return nil +func (cp *Processor) checkEACLOwnership(binTable []byte, key *keys.PublicKey) error { + // unmarshal table + table := eacl.NewTable() + + err := table.Unmarshal(binTable) + if err != nil { + return fmt.Errorf("invalid binary table: %w", err) + } + + // receive owner of the related container + cnr, err := cp.cnrClient.Get(table.CID()) + if err != nil { + return fmt.Errorf("could not receive the container: %w", err) + } + + ownerID := cnr.OwnerID() + + // check key ownership + ownerKeys, err := cp.idClient.AccountKeys(ownerID) + if err != nil { + return fmt.Errorf("could not received owner keys %s: %w", ownerID, err) + } + + for _, ownerKey := range ownerKeys { + if ownerKey.Equal(key) { + return nil + } + } + + return fmt.Errorf("key %s is not tied to the owner of the container", key) } func (cp *Processor) approveSetEACL(e container.SetEACL) { diff --git a/pkg/innerring/processors/container/processor.go b/pkg/innerring/processors/container/processor.go index de664754e6..aec59b6da5 100644 --- a/pkg/innerring/processors/container/processor.go +++ b/pkg/innerring/processors/container/processor.go @@ -8,6 +8,7 @@ import ( "github.com/nspcc-dev/neofs-node/pkg/innerring/config" "github.com/nspcc-dev/neofs-node/pkg/morph/client" "github.com/nspcc-dev/neofs-node/pkg/morph/client/container/wrapper" + neofsid "github.com/nspcc-dev/neofs-node/pkg/morph/client/neofsid/wrapper" "github.com/nspcc-dev/neofs-node/pkg/morph/event" containerEvent "github.com/nspcc-dev/neofs-node/pkg/morph/event/container" "github.com/panjf2000/ants/v2" @@ -29,6 +30,7 @@ type ( alphabetState AlphabetState feeProvider *config.FeeConfig cnrClient *wrapper.Wrapper + idClient *neofsid.ClientWrapper } // Params of the processor constructor.