Improve payload validation

This commit is contained in:
mcrakhman 2023-04-21 23:21:49 +02:00 committed by Mikhail Iudin
parent 0281f006e6
commit 5da565f68c
No known key found for this signature in database
GPG Key ID: FAAAA8BAABDFF1C0
3 changed files with 32 additions and 68 deletions

View File

@ -1,7 +1,6 @@
package commonspace package commonspace
import ( import (
"fmt"
"github.com/anytypeio/any-sync/commonspace/object/acl/aclrecordproto" "github.com/anytypeio/any-sync/commonspace/object/acl/aclrecordproto"
"github.com/anytypeio/any-sync/commonspace/object/acl/list" "github.com/anytypeio/any-sync/commonspace/object/acl/list"
"github.com/anytypeio/any-sync/commonspace/object/tree/objecttree" "github.com/anytypeio/any-sync/commonspace/object/tree/objecttree"
@ -188,7 +187,7 @@ func storagePayloadForSpaceDerive(payload SpaceDerivePayload) (storagePayload sp
} }
func validateSpaceStorageCreatePayload(payload spacestorage.SpaceStorageCreatePayload) (err error) { func validateSpaceStorageCreatePayload(payload spacestorage.SpaceStorageCreatePayload) (err error) {
err = validateCreateSpaceHeaderPayload(payload.SpaceHeaderWithId) err = ValidateSpaceHeader(payload.SpaceHeaderWithId, nil)
if err != nil { if err != nil {
return return
} }
@ -211,7 +210,16 @@ func validateSpaceStorageCreatePayload(payload spacestorage.SpaceStorageCreatePa
return return
} }
func validateCreateSpaceHeaderPayload(rawHeaderWithId *spacesyncproto.RawSpaceHeaderWithId) (err error) { func ValidateSpaceHeader(rawHeaderWithId *spacesyncproto.RawSpaceHeaderWithId, identity crypto.PubKey) (err error) {
sepIdx := strings.Index(rawHeaderWithId.Id, ".")
if sepIdx == -1 {
err = objecttree.ErrIncorrectCid
return
}
if !cidutil.VerifyCid(rawHeaderWithId.RawHeader, rawHeaderWithId.Id[:sepIdx]) {
err = objecttree.ErrIncorrectCid
return
}
var rawSpaceHeader spacesyncproto.RawSpaceHeader var rawSpaceHeader spacesyncproto.RawSpaceHeader
err = proto.Unmarshal(rawHeaderWithId.RawHeader, &rawSpaceHeader) err = proto.Unmarshal(rawHeaderWithId.RawHeader, &rawSpaceHeader)
if err != nil { if err != nil {
@ -222,14 +230,6 @@ func validateCreateSpaceHeaderPayload(rawHeaderWithId *spacesyncproto.RawSpaceHe
if err != nil { if err != nil {
return return
} }
split := strings.Split(rawHeaderWithId.Id, ".")
if len(split) != 2 {
return spacestorage.ErrIncorrectSpaceHeader
}
if !cidutil.VerifyCid(rawHeaderWithId.RawHeader, split[0]) {
err = objecttree.ErrIncorrectCid
return
}
payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(header.Identity) payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(header.Identity)
if err != nil { if err != nil {
return return
@ -239,16 +239,17 @@ func validateCreateSpaceHeaderPayload(rawHeaderWithId *spacesyncproto.RawSpaceHe
err = spacestorage.ErrIncorrectSpaceHeader err = spacestorage.ErrIncorrectSpaceHeader
return return
} }
id, err := cidutil.NewCidFromBytes(rawHeaderWithId.RawHeader) if rawHeaderWithId.Id[sepIdx+1:] != strconv.FormatUint(header.ReplicationKey, 36) {
if err != nil { err = spacestorage.ErrIncorrectSpaceHeader
return return
} }
requiredSpaceId := fmt.Sprintf("%s.%s", id, strconv.FormatUint(header.ReplicationKey, 36)) if identity == nil {
if requiredSpaceId != rawHeaderWithId.Id { return
}
if !payloadIdentity.Equals(identity) {
err = spacestorage.ErrIncorrectSpaceHeader err = spacestorage.ErrIncorrectSpaceHeader
return return
} }
return return
} }
@ -295,6 +296,10 @@ func validateCreateSpaceAclPayload(rawWithId *aclrecordproto.RawAclRecordWithId)
} }
func validateCreateSpaceSettingsPayload(rawWithId *treechangeproto.RawTreeChangeWithId) (aclHeadId string, spaceId string, err error) { func validateCreateSpaceSettingsPayload(rawWithId *treechangeproto.RawTreeChangeWithId) (aclHeadId string, spaceId string, err error) {
if !cidutil.VerifyCid(rawWithId.RawChange, rawWithId.Id) {
err = spacestorage.ErrIncorrectSpaceHeader
return
}
var raw treechangeproto.RawTreeChange var raw treechangeproto.RawTreeChange
err = proto.Unmarshal(rawWithId.RawChange, &raw) err = proto.Unmarshal(rawWithId.RawChange, &raw)
if err != nil { if err != nil {
@ -314,49 +319,8 @@ func validateCreateSpaceSettingsPayload(rawWithId *treechangeproto.RawTreeChange
err = spacestorage.ErrIncorrectSpaceHeader err = spacestorage.ErrIncorrectSpaceHeader
return return
} }
id, err := cidutil.NewCidFromBytes(rawWithId.RawChange)
if id != rawWithId.Id {
err = spacestorage.ErrIncorrectSpaceHeader
return
}
spaceId = rootChange.SpaceId spaceId = rootChange.SpaceId
aclHeadId = rootChange.AclHeadId aclHeadId = rootChange.AclHeadId
return return
} }
// ValidateSpaceHeader Used in coordinator
func ValidateSpaceHeader(spaceId string, header []byte, identity crypto.PubKey) (err error) {
split := strings.Split(spaceId, ".")
if len(split) != 2 {
return spacestorage.ErrIncorrectSpaceHeader
}
if !cidutil.VerifyCid(header, split[0]) {
err = objecttree.ErrIncorrectCid
return
}
raw := &spacesyncproto.RawSpaceHeader{}
err = proto.Unmarshal(header, raw)
if err != nil {
return
}
payload := &spacesyncproto.SpaceHeader{}
err = proto.Unmarshal(raw.SpaceHeader, payload)
if err != nil {
return
}
payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(payload.Identity)
if err != nil {
return
}
if identity != nil && !payloadIdentity.Equals(identity) {
err = spacestorage.ErrIncorrectSpaceHeader
return
}
res, err := identity.Verify(raw.SpaceHeader, raw.Signature)
if err != nil || !res {
err = spacestorage.ErrIncorrectSpaceHeader
return
}
return
}

View File

@ -23,7 +23,7 @@ func TestSuccessHeaderPayloadForSpaceCreate(t *testing.T) {
require.NoError(t, err) require.NoError(t, err)
_, rawHeaderWithId, err := rawHeaderWithId(accountKeys) _, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err) require.NoError(t, err)
err = validateCreateSpaceHeaderPayload(rawHeaderWithId) err = ValidateSpaceHeader(rawHeaderWithId, nil)
require.NoError(t, err) require.NoError(t, err)
} }
@ -64,7 +64,7 @@ func TestFailedHeaderPayloadForSpaceCreate_InvalidFormatSpaceId(t *testing.T) {
RawHeader: marhalledRawHeader, RawHeader: marhalledRawHeader,
Id: spaceId, Id: spaceId,
} }
err = validateCreateSpaceHeaderPayload(rawHeaderWithId) err = ValidateSpaceHeader(rawHeaderWithId, nil)
assert.EqualErrorf(t, err, spacestorage.ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", spacestorage.ErrIncorrectSpaceHeader, err) assert.EqualErrorf(t, err, spacestorage.ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", spacestorage.ErrIncorrectSpaceHeader, err)
} }
@ -104,7 +104,7 @@ func TestFailedHeaderPayloadForSpaceCreate_CidIsWrong(t *testing.T) {
RawHeader: marhalledRawHeader, RawHeader: marhalledRawHeader,
Id: spaceId, Id: spaceId,
} }
err = validateCreateSpaceHeaderPayload(rawHeaderWithId) err = ValidateSpaceHeader(rawHeaderWithId, nil)
assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err) assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err)
} }
@ -145,7 +145,7 @@ func TestFailedHeaderPayloadForSpaceCreate_SignedWithAnotherIdentity(t *testing.
RawHeader: marhalledRawHeader, RawHeader: marhalledRawHeader,
Id: spaceId, Id: spaceId,
} }
err = validateCreateSpaceHeaderPayload(rawHeaderWithId) err = ValidateSpaceHeader(rawHeaderWithId, nil)
assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err) assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err)
} }
@ -637,17 +637,17 @@ func rawHeaderWithId(accountKeys *accountdata.AccountKeys) (spaceId string, rawW
SpaceHeader: marhalled, SpaceHeader: marhalled,
Signature: signature, Signature: signature,
} }
marhalledRawHeader, err := rawHeader.Marshal() marshalledRawHeader, err := rawHeader.Marshal()
if err != nil { if err != nil {
return return
} }
id, err := cidutil.NewCidFromBytes(marhalledRawHeader) id, err := cidutil.NewCidFromBytes(marshalledRawHeader)
if err != nil { if err != nil {
return return
} }
spaceId = fmt.Sprintf("%s.%s", id, strconv.FormatUint(replicationKey, 36)) spaceId = fmt.Sprintf("%s.%s", id, strconv.FormatUint(replicationKey, 36))
rawWithId = &spacesyncproto.RawSpaceHeaderWithId{ rawWithId = &spacesyncproto.RawSpaceHeaderWithId{
RawHeader: marhalledRawHeader, RawHeader: marshalledRawHeader,
Id: spaceId, Id: spaceId,
} }

View File

@ -3,7 +3,6 @@ package commonspace
import ( import (
"context" "context"
"errors" "errors"
"fmt"
"github.com/anytypeio/any-sync/accountservice" "github.com/anytypeio/any-sync/accountservice"
"github.com/anytypeio/any-sync/app/logger" "github.com/anytypeio/any-sync/app/logger"
"github.com/anytypeio/any-sync/commonspace/headsync" "github.com/anytypeio/any-sync/commonspace/headsync"
@ -30,6 +29,7 @@ import (
"github.com/zeebo/errs" "github.com/zeebo/errs"
"go.uber.org/zap" "go.uber.org/zap"
"strconv" "strconv"
"strings"
"sync" "sync"
"sync/atomic" "sync/atomic"
"time" "time"
@ -77,7 +77,7 @@ type SpaceDescription struct {
} }
func NewSpaceId(id string, repKey uint64) string { func NewSpaceId(id string, repKey uint64) string {
return fmt.Sprintf("%s.%s", id, strconv.FormatUint(repKey, 36)) return strings.Join([]string{id, strconv.FormatUint(repKey, 36)}, ".")
} }
type Space interface { type Space interface {