Skip to content
Snippets Groups Projects
Commit 4decb591 authored by Jake Taylor's avatar Jake Taylor :lips:
Browse files

Merge branch 'hotfix/authstore' into 'release'

Auth Store Fixes

See merge request !282
parents d66e7529 8119e512
No related branches found
No related tags found
2 merge requests!510Release,!282Auth Store Fixes
......@@ -110,7 +110,8 @@ func NewStateLegacy(kv *versioned.KV, net cmix.Client, e2e e2e.Handler,
}, &receivedRequestService{s: s, reset: true})
if err != nil {
return nil, errors.Errorf("Failed to make Auth State manager")
return nil, errors.WithMessage(err,
"Failed to make Auth State manager")
}
return s, nil
......
......@@ -9,20 +9,21 @@ package store
import (
"bytes"
"encoding/base64"
"encoding/binary"
"encoding/json"
"github.com/pkg/errors"
jww "github.com/spf13/jwalterweatherman"
"gitlab.com/elixxir/client/storage/versioned"
"gitlab.com/elixxir/crypto/e2e/auth"
"gitlab.com/elixxir/ekv"
"gitlab.com/xx_network/primitives/id"
"gitlab.com/xx_network/primitives/netTime"
"strings"
)
const (
negotiationPartnersKey = "NegotiationPartners"
negotiationPartnersVersion = 0
negotiationPartnersVersion = 1
negotiationFingerprintsKeyPrefix = "NegotiationFingerprints/"
currentNegotiationFingerprintsVersion = 0
)
......@@ -119,20 +120,22 @@ func (s *Store) savePreviousNegotiations() error {
func (s *Store) newOrLoadPreviousNegotiations() (map[id.ID]bool, error) {
obj, err := s.kv.Get(negotiationPartnersKey, negotiationPartnersVersion)
if err != nil {
if strings.Contains(err.Error(), "object not found") {
newPreviousNegotiations := make(map[id.ID]bool)
obj := &versioned.Object{
Version: negotiationPartnersVersion,
Timestamp: netTime.Now(),
Data: marshalPreviousNegotiations(newPreviousNegotiations),
}
err = s.kv.Set(negotiationPartnersKey, negotiationPartnersVersion, obj)
if err != nil {
return nil, err
}
return newPreviousNegotiations, nil
// V0 Upgrade Path
if !ekv.Exists(err) {
upgradeErr := upgradePreviousNegotiationsV0(s.kv)
if upgradeErr != nil {
return nil, errors.Wrapf(err, "%+v", upgradeErr)
}
obj, err = s.kv.Get(negotiationPartnersKey,
negotiationPartnersVersion)
}
// Note: if it still doesn't exist, return an empty one.
if err != nil && !ekv.Exists(err) {
newPreviousNegotiations := make(map[id.ID]bool)
return newPreviousNegotiations, nil
} else if err != nil {
return nil, err
}
......@@ -192,8 +195,8 @@ func saveNegotiationFingerprints(
// loadNegotiationFingerprints loads the list of sentByFingerprints for the given
// partner from storage.
func loadNegotiationFingerprints(partner *id.ID, kv *versioned.KV) ([][]byte, error) {
obj, err := kv.Get(makeNegotiationFingerprintsKey(partner),
currentNegotiationFingerprintsVersion)
fpKey := makeNegotiationFingerprintsKey(partner)
obj, err := kv.Get(fpKey, currentNegotiationFingerprintsVersion)
if err != nil {
return nil, err
}
......@@ -239,6 +242,50 @@ func unmarshalNegotiationFingerprints(buf []byte) [][]byte {
// makeOldNegotiationFingerprintsKey generates the key used to load and store
// negotiation sentByFingerprints for the partner.
func makeNegotiationFingerprintsKey(partner *id.ID) string {
return negotiationFingerprintsKeyPrefix +
string(base64.StdEncoding.EncodeToString(partner.Marshal()))
return negotiationFingerprintsKeyPrefix + partner.String()
}
// Historical functions
// unmarshalPreviousNegotiations unmarshalls the marshalled byte slice into a
// list of partner IDs.
func unmarshalPreviousNegotiationsV0(buf []byte) map[id.ID]struct{} {
buff := bytes.NewBuffer(buf)
numberOfPartners := binary.LittleEndian.Uint64(buff.Next(8))
partners := make(map[id.ID]struct{}, numberOfPartners)
for i := uint64(0); i < numberOfPartners; i++ {
partner, err := id.Unmarshal(buff.Next(id.ArrIDLen))
if err != nil {
jww.FATAL.Panicf(
"Failed to unmarshal negotiation partner ID: %+v", err)
}
partners[*partner] = struct{}{}
}
return partners
}
// upgradePreviousNegotiationsV0 upgrades the negotiations Partners key from V0
// to V1
func upgradePreviousNegotiationsV0(kv *versioned.KV) error {
obj, err := kv.Get(negotiationPartnersKey, 0)
if !ekv.Exists(err) {
return nil
}
old := unmarshalPreviousNegotiationsV0(obj.Data)
newPrevNegotiations := make(map[id.ID]bool)
for id := range old {
newPrevNegotiations[id] = true
}
obj = &versioned.Object{
Version: negotiationPartnersVersion,
Timestamp: netTime.Now(),
Data: marshalPreviousNegotiations(
newPrevNegotiations),
}
return kv.Set(negotiationPartnersKey, negotiationPartnersVersion, obj)
}
package store
import (
"encoding/base64"
"sync"
"github.com/cloudflare/circl/dh/sidh"
......@@ -11,6 +10,7 @@ import (
util "gitlab.com/elixxir/client/storage/utility"
"gitlab.com/elixxir/client/storage/versioned"
"gitlab.com/elixxir/crypto/contact"
"gitlab.com/elixxir/ekv"
"gitlab.com/xx_network/primitives/id"
)
......@@ -77,10 +77,12 @@ func loadReceivedRequest(kv *versioned.KV, partner *id.ID) (
}
round, err := rounds.LoadRound(kv, makeRoundKey(partner))
if err != nil {
if err != nil && ekv.Exists(err) {
return nil, errors.WithMessagef(err, "Failed to Load "+
"round request was received on with %s",
partner)
} else if err != nil && !ekv.Exists(err) {
jww.WARN.Printf("No round info for partner %s", partner)
}
return &ReceivedRequest{
......@@ -120,6 +122,5 @@ func (rr *ReceivedRequest) getType() RequestType {
}
func makeRoundKey(partner *id.ID) string {
return "receivedRequestRound:" +
base64.StdEncoding.EncodeToString(partner.Marshal())
return "receivedRequestRound:" + partner.String()
}
......@@ -8,9 +8,9 @@
package store
import (
"encoding/base64"
"encoding/hex"
"encoding/json"
"fmt"
"sync"
"github.com/cloudflare/circl/dh/sidh"
......@@ -19,12 +19,13 @@ import (
sidhinterface "gitlab.com/elixxir/client/interfaces/sidh"
"gitlab.com/elixxir/client/storage/versioned"
"gitlab.com/elixxir/crypto/cyclic"
"gitlab.com/elixxir/ekv"
"gitlab.com/elixxir/primitives/format"
"gitlab.com/xx_network/primitives/id"
"gitlab.com/xx_network/primitives/netTime"
)
const currentSentRequestVersion = 0
const currentSentRequestVersion = 1
type SentRequest struct {
kv *versioned.KV
......@@ -73,8 +74,16 @@ func newSentRequest(kv *versioned.KV, partner *id.ID, partnerHistoricalPubKey,
func loadSentRequest(kv *versioned.KV, partner *id.ID, grp *cyclic.Group) (*SentRequest, error) {
srKey := makeSentRequestKey(partner)
obj, err := kv.Get(srKey,
currentSentRequestVersion)
obj, err := kv.Get(srKey, currentSentRequestVersion)
// V0 Upgrade Path
if !ekv.Exists(err) {
upgradeErr := upgradeSentRequestKeyV0(kv, partner)
if upgradeErr != nil {
return nil, errors.Wrapf(err, "%+v", upgradeErr)
}
obj, err = kv.Get(srKey, currentSentRequestVersion)
}
if err != nil {
return nil, errors.WithMessagef(err, "Failed to Load "+
......@@ -260,6 +269,37 @@ func (sr *SentRequest) getType() RequestType {
return Sent
}
// makeSentRequestKey makes the key string for accessing the
// partners sent request object from the key value store.
func makeSentRequestKey(partner *id.ID) string {
return "sentRequest:" + base64.StdEncoding.EncodeToString(partner.Marshal())
return "sentRequest:" + partner.String()
}
// V0 Utility Functions
// makeSentRequestKeyV0 The old key used the string pattern
// "Partner:PartnerID" instead of "sentRequest:PartnerID".
func makeSentRequestKeyV0(partner *id.ID) string {
return fmt.Sprintf("Partner:%v", partner.String())
}
// upgradeSentRequestKeyV0 upgrads the srKey from version 0 to 1 by
// changing the version number.
func upgradeSentRequestKeyV0(kv *versioned.KV, partner *id.ID) error {
oldKey := makeSentRequestKeyV0(partner)
obj, err := kv.Get(oldKey, 0)
if err != nil {
return err
}
jww.INFO.Printf("Upgrading legacy srKey for %s", partner)
// Note: uses same encoding, just different keys
obj.Version = 1
err = kv.Set(makeSentRequestKey(partner), 1, obj)
if err != nil {
return err
}
return kv.Delete(oldKey, 0)
}
......@@ -104,10 +104,11 @@ func (r *Ratchet) AddPartner(partnerID *id.ID,
myID := r.myID
jww.INFO.Printf("Adding Partner %s:\n\tMy Private Key: %s"+
myPubKey := diffieHellman.GeneratePublicKey(myPrivKey, r.grp)
jww.INFO.Printf("Adding Partner %s:\n\tMy Public Key: %s"+
"\n\tPartner Public Key: %s to %s",
partnerID,
myPrivKey.TextVerbose(16, 0),
myPubKey.TextVerbose(16, 0),
partnerPubKey.TextVerbose(16, 0), myID)
mid := *partnerID
......
......@@ -9,6 +9,7 @@ package utility
import (
"fmt"
"gitlab.com/elixxir/client/storage/versioned"
"gitlab.com/elixxir/crypto/contact"
"gitlab.com/xx_network/primitives/id"
......@@ -17,6 +18,14 @@ import (
const currentContactVersion = 0
// StoreContact writes a contact into a versioned.KV using the
// contact ID as the key.
//
// Parameters:
// * kv - the key value store to write the contact.
// * c - the contact object to store.
// Returns:
// * error if the write fails to succeed for any reason.
func StoreContact(kv *versioned.KV, c contact.Contact) error {
now := netTime.Now()
......@@ -29,6 +38,15 @@ func StoreContact(kv *versioned.KV, c contact.Contact) error {
return kv.Set(makeContactKey(c.ID), currentContactVersion, &obj)
}
// LoadContact reads a contact from a versioned.KV vie their contact ID.
//
// Parameters:
// * kv - the key value store to read the contact
// * cid - the contacts unique *id.ID to load
// Returns:
// * contact.Contact object populated with the user info, or empty on error.
// * version number of the contact loaded.
// * error if an error occurs, or nil otherwise
func LoadContact(kv *versioned.KV, cid *id.ID) (contact.Contact, error) {
vo, err := kv.Get(makeContactKey(cid), currentContactVersion)
if err != nil {
......@@ -38,6 +56,13 @@ func LoadContact(kv *versioned.KV, cid *id.ID) (contact.Contact, error) {
return contact.Unmarshal(vo.Data)
}
// DeleteContact removes the contact identified by cid from the kv.
//
// Parameters:
// - kv - the key value store to delete from
// - cid - the contacts unique *id.ID to delete
// Returns:
// - error if an error occurs or nil otherwise
func DeleteContact(kv *versioned.KV, cid *id.ID) error {
return kv.Delete(makeContactKey(cid), currentContactVersion)
}
......
......@@ -93,9 +93,10 @@ func loginLegacy(net *Cmix, callbacks AuthCallbacks,
return nil, errors.WithMessage(err, "Failed to add the e2e processes")
}
m.auth, err = auth.NewState(net.GetStorage().GetKV(), net.GetCmix(),
m.e2e, net.GetRng(), net.GetEventReporter(), params.Auth,
params.Session, MakeAuthCallbacksAdapter(callbacks, m),
m.auth, err = auth.NewStateLegacy(net.GetStorage().GetKV(),
net.GetCmix(), m.e2e, net.GetRng(), net.GetEventReporter(),
params.Auth, params.Session,
MakeAuthCallbacksAdapter(callbacks, m),
m.backup.TriggerBackup)
if err != nil {
return nil, err
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment