diff --git a/api/client.go b/api/client.go index 97241cf2919891313a25849335efde607e4272b0..7c23d024a5996778319aa06a78ee659909aa13ac 100644 --- a/api/client.go +++ b/api/client.go @@ -716,6 +716,11 @@ func (c *Client) GetE2EHandler() e2e.Handler { return c.e2e } +// GetEventReporter returns the event reporter +func (c *Client) GetEventReporter() event.Reporter { + return c.events +} + // GetBackup returns a pointer to the backup container so that the backup can be // set and triggered. func (c *Client) GetBackup() *backup.Backup { diff --git a/api/precan.go b/api/precan.go index f85210df17ac5f37845201cedb1b68430f6b12e3..a563faa230bf83a0bca8da52330cf9d1262f8b42 100644 --- a/api/precan.go +++ b/api/precan.go @@ -9,6 +9,7 @@ package api import ( "encoding/binary" + "gitlab.com/elixxir/crypto/diffieHellman" "math/rand" "github.com/cloudflare/circl/dh/sidh" @@ -33,10 +34,7 @@ func createPrecannedUser(precannedID uint, rng csprng.Source, cmix, prng := rand.New(rand.NewSource(int64(precannedID))) prime := e2e.GetPBytes() keyLen := len(prime) - e2eKeyBytes, err := csprng.GenerateInGroup(prime, keyLen, prng) - if err != nil { - jww.FATAL.Panicf(err.Error()) - } + e2eKey := diffieHellman.GeneratePrivateKey(keyLen, e2e, prng) // Salt, UID, etc gen salt := make([]byte, SaltSize) @@ -57,7 +55,8 @@ func createPrecannedUser(precannedID uint, rng csprng.Source, cmix, ReceptionID: &userID, ReceptionSalt: salt, Precanned: true, - E2eDhPrivateKey: e2e.NewIntFromBytes(e2eKeyBytes), + E2eDhPrivateKey: e2eKey, + E2eDhPublicKey: diffieHellman.GeneratePublicKey(e2eKey, e2e), TransmissionRSA: rsaKey, ReceptionRSA: rsaKey, } diff --git a/api/user.go b/api/user.go index 5913185b4bec08d63680a9e2e3d89d6632dca736..f0538a1a9a092512d6619c291f393679a81e32e9 100644 --- a/api/user.go +++ b/api/user.go @@ -8,6 +8,7 @@ package api import ( + "gitlab.com/elixxir/crypto/diffieHellman" "regexp" "runtime" "strings" @@ -33,10 +34,10 @@ func createNewUser(rng *fastRNG.StreamGenerator, cmix, e2e *cyclic.Group) user.Info { // CMIX Keygen var transmissionRsaKey, receptionRsaKey *rsa.PrivateKey + var e2eKey *cyclic.Int + var transmissionSalt, receptionSalt []byte - var e2eKeyBytes, transmissionSalt, receptionSalt []byte - - e2eKeyBytes, transmissionSalt, receptionSalt, + transmissionSalt, receptionSalt, e2eKey, transmissionRsaKey, receptionRsaKey = createKeys(rng, e2e) // Salt, UID, etc gen @@ -85,13 +86,14 @@ func createNewUser(rng *fastRNG.StreamGenerator, cmix, ReceptionSalt: receptionSalt, ReceptionRSA: receptionRsaKey, Precanned: false, - E2eDhPrivateKey: e2e.NewIntFromBytes(e2eKeyBytes), + E2eDhPrivateKey: e2eKey, + E2eDhPublicKey: diffieHellman.GeneratePublicKey(e2eKey, e2e), } } func createKeys(rng *fastRNG.StreamGenerator, - e2e *cyclic.Group) (e2eKeyBytes, - transmissionSalt, receptionSalt []byte, + e2e *cyclic.Group) ( + transmissionSalt, receptionSalt []byte, e2eKey *cyclic.Int, transmissionRsaKey, receptionRsaKey *rsa.PrivateKey) { wg := sync.WaitGroup{} @@ -101,9 +103,7 @@ func createKeys(rng *fastRNG.StreamGenerator, defer wg.Done() var err error rngStream := rng.GetStream() - prime := e2e.GetPBytes() - keyLen := len(prime) - e2eKeyBytes, err = csprng.GenerateInGroup(prime, keyLen, + e2eKey = diffieHellman.GeneratePrivateKey(len(e2e.GetPBytes()), e2e, rngStream) rngStream.Close() if err != nil { @@ -148,10 +148,8 @@ func createNewVanityUser(rng csprng.Source, cmix, // DH Keygen prime := e2e.GetPBytes() keyLen := len(prime) - e2eKeyBytes, err := csprng.GenerateInGroup(prime, keyLen, rng) - if err != nil { - jww.FATAL.Panicf(err.Error()) - } + + e2eKey := diffieHellman.GeneratePrivateKey(keyLen, e2e, rng) // RSA Keygen (4096 bit defaults) transmissionRsaKey, err := rsa.GenerateKey(rng, rsa.DefaultRSABitLen) @@ -261,6 +259,7 @@ func createNewVanityUser(rng csprng.Source, cmix, ReceptionSalt: receptionSalt, ReceptionRSA: receptionRsaKey, Precanned: false, - E2eDhPrivateKey: e2e.NewIntFromBytes(e2eKeyBytes), + E2eDhPrivateKey: e2eKey, + E2eDhPublicKey: diffieHellman.GeneratePublicKey(e2eKey, e2e), } } diff --git a/bindings/ud.go b/bindings/ud.go index 23195fd751822311853a869cf92f0c4bbb2b48b5..ea8f5390abb2b749d14c50b10ec21b9bf8e596d5 100644 --- a/bindings/ud.go +++ b/bindings/ud.go @@ -41,8 +41,8 @@ func NewUserDiscovery(client *Client, username string) (*UserDiscovery, error) { stream := client.api.GetRng().GetStream() defer stream.Close() m, err := udPackage.NewManager(client.api.GetNetworkInterface(), - client.api.GetE2e(), client.api.NetworkFollowerStatus, - client.api.GetEventManager(), + client.api.GetE2EHandler(), client.api.NetworkFollowerStatus, + client.api.GetEventReporter(), client.api.GetComms(), client.api.GetStorage(), stream, username, client.api.GetStorage().GetKV()) @@ -60,7 +60,7 @@ func NewUserDiscovery(client *Client, username string) (*UserDiscovery, error) { // instantiation of the manager by NewUserDiscovery. func LoadUserDiscovery(client *Client) (*UserDiscovery, error) { m, err := udPackage.LoadManager(client.api.GetNetworkInterface(), - client.api.GetE2e(), client.api.GetEventManager(), + client.api.GetE2EHandler(), client.api.GetEventReporter(), client.api.GetComms(), client.api.GetStorage(), client.api.GetStorage().GetKV()) @@ -119,7 +119,11 @@ func NewUserDiscoveryFromBackup(client *Client, "registered phone number") } - m, err := udPackage.NewManagerFromBackup(client.api.GetNetworkInterface(), client.api.GetE2e(), client.api.NetworkFollowerStatus, client.api.GetEventManager(), client.api.GetComms(), client.api.GetStorage(), emailFact, phoneFact, client.api.GetStorage().GetKV()) + m, err := udPackage.NewManagerFromBackup(client.api.GetNetworkInterface(), + client.api.GetE2EHandler(), client.api.NetworkFollowerStatus, + client.api.GetEventReporter(), client.api.GetComms(), + client.api.GetStorage(), emailFact, phoneFact, + client.api.GetStorage().GetKV()) if err != nil { return nil, errors.WithMessage(err, "Failed to create User Discovery Manager") @@ -228,8 +232,8 @@ func (ud UserDiscovery) Search(client *Client, } rids, _, err := udPackage.Search( - client.api.GetNetworkInterface(), client.api.GetEventManager(), - stream, client.api.GetE2e().GetGroup(), udContact, + client.api.GetNetworkInterface(), client.api.GetEventReporter(), + stream, client.api.GetE2EHandler().GetGroup(), udContact, cb, factList, p) if err != nil { @@ -285,8 +289,8 @@ func (ud UserDiscovery) SearchSingle(client *Client, f string, callback SingleSe } rids, _, err := udPackage.Search(client.api.GetNetworkInterface(), - client.api.GetEventManager(), - stream, client.api.GetE2e().GetGroup(), udContact, + client.api.GetEventReporter(), + stream, client.api.GetE2EHandler().GetGroup(), udContact, cb, []fact.Fact{fObj}, p) if err != nil { @@ -361,7 +365,7 @@ func (ud UserDiscovery) Lookup(client *Client, } rid, _, err := udPackage.Lookup(client.api.GetNetworkInterface(), - stream, client.api.GetE2e().GetGroup(), + stream, client.api.GetE2EHandler().GetGroup(), udContact, cb, uid, p) @@ -447,7 +451,7 @@ func (ud UserDiscovery) MultiLookup(client *Client, stream := client.api.GetRng().GetStream() defer stream.Close() _, _, err := udPackage.Lookup(client.api.GetNetworkInterface(), - stream, client.api.GetE2e().GetGroup(), + stream, client.api.GetE2EHandler().GetGroup(), udContact, cb, localID, p) if err != nil { results <- lookupResponse{ diff --git a/cmd/ud.go b/cmd/ud.go index 9a74663735f4e696949267d94addc1b27660dbfc..431f774f3f6d56f81fca53f2709b1f00903caf9a 100644 --- a/cmd/ud.go +++ b/cmd/ud.go @@ -10,6 +10,13 @@ package cmd import ( "fmt" + "gitlab.com/elixxir/client/single" + "gitlab.com/elixxir/client/ud" + "gitlab.com/elixxir/client/xxmutils" + "gitlab.com/elixxir/primitives/fact" + "gitlab.com/xx_network/primitives/utils" + "strings" + "time" "github.com/spf13/cobra" jww "github.com/spf13/jwalterweatherman" @@ -26,12 +33,12 @@ var udCmd = &cobra.Command{ Short: "Register for and search users using the xx network user discovery service.", Args: cobra.NoArgs, Run: func(cmd *cobra.Command, args []string) { - // client := initClient() + client := initClient() - // // get user and save contact to file - // user := client.GetUser() - // jww.INFO.Printf("User: %s", user.ReceptionID) - // writeContact(user.GetContact()) + // get user and save contact to file + user := client.GetUser() + jww.INFO.Printf("User: %s", user.ReceptionID) + writeContact(user.GetContact()) // // Set up reception handler // swBoard := client.GetSwitchboard() @@ -57,194 +64,211 @@ var udCmd = &cobra.Command{ // }) // } - // err := client.StartNetworkFollower(50 * time.Millisecond) - // if err != nil { - // jww.FATAL.Panicf("%+v", err) - // } - - // // Wait until connected or crash on timeout - // connected := make(chan bool, 10) - // client.GetHealth().AddChannel(connected) - // waitUntilConnected(connected) - - // // Make single-use manager and start receiving process - // singleMng := old.NewManager(client) - // err = client.AddService(singleMng.StartProcesses) - // if err != nil { - // jww.FATAL.Panicf("Failed to add single use process: %+v", err) - // } - - // // Make user discovery manager - // userDiscoveryMgr, err := ud.NewManager(client, singleMng) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new UD manager: %+v", err) - // } - - // userToRegister := viper.GetString("register") - // if userToRegister != "" { - // err = userDiscoveryMgr.Register(userToRegister) - // if err != nil { - // fmt.Printf("Failed to register user %s: %s\n", - // userToRegister, err.Error()) - // jww.FATAL.Panicf("Failed to register user %s: %+v", userToRegister, err) - // } - // } - - // var newFacts fact.FactList - // phone := viper.GetString("addphone") - // if phone != "" { - // f, err := fact.NewFact(fact.Phone, phone) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new fact: %+v", err) - // } - // newFacts = append(newFacts, f) - // } - - // email := viper.GetString("addemail") - // if email != "" { - // f, err := fact.NewFact(fact.Email, email) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new fact: %+v", err) - // } - // newFacts = append(newFacts, f) - // } - - // for i := 0; i < len(newFacts); i++ { - // r, err := userDiscoveryMgr.SendRegisterFact(newFacts[i]) - // if err != nil { - // fmt.Printf("Failed to register fact: %s\n", - // newFacts[i]) - // jww.FATAL.Panicf("Failed to send register fact: %+v", err) - // } - // // TODO Store the code? - // jww.INFO.Printf("Fact Add Response: %+v", r) - // } - - // confirmID := viper.GetString("confirm") - // if confirmID != "" { - // err = userDiscoveryMgr.SendConfirmFact(confirmID, confirmID) - // if err != nil { - // fmt.Printf("Couldn't confirm fact: %s\n", - // err.Error()) - // jww.FATAL.Panicf("%+v", err) - // } - // } - - // // Handle lookup (verification) process - // // Note: Cryptographic verification occurs above the bindings layer - // lookupIDStr := viper.GetString("lookup") - // if lookupIDStr != "" { - // lookupID, _ := parseRecipient(lookupIDStr) - // //if !ok { - // // jww.FATAL.Panicf("Could not parse recipient: %s", lookupIDStr) - // //} - // err = userDiscoveryMgr.Lookup(lookupID, - // func(newContact contact.Contact, err error) { - // if err != nil { - // jww.FATAL.Panicf("UserDiscovery Lookup error: %+v", err) - // } - // printContact(newContact) - // }, 30*time.Second) - - // if err != nil { - // jww.WARN.Printf("Failed UD lookup: %+v", err) - // } - - // time.Sleep(31 * time.Second) - // } - - // if viper.GetString("batchadd") != "" { - // idListFile, err := utils.ReadFile(viper.GetString("batchadd")) - // if err != nil { - // fmt.Printf("BATCHADD: Couldn't read file: %s\n", - // err.Error()) - // jww.FATAL.Panicf("BATCHADD: Couldn't read file: %+v", err) - // } - // restored, _, _, err := xxmutils.RestoreContactsFromBackup( - // idListFile, client, userDiscoveryMgr, nil) - // if err != nil { - // jww.FATAL.Panicf("%+v", err) - // } - // for i := 0; i < len(restored); i++ { - // uid := restored[i] - // for !client.HasAuthenticatedChannel(uid) { - // time.Sleep(time.Second) - // } - // jww.INFO.Printf("Authenticated channel established for %s", uid) - // } - // } - // usernameSearchStr := viper.GetString("searchusername") - // emailSearchStr := viper.GetString("searchemail") - // phoneSearchStr := viper.GetString("searchphone") - - // var facts fact.FactList - // if usernameSearchStr != "" { - // f, err := fact.NewFact(fact.Username, usernameSearchStr) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new fact: %+v", err) - // } - // facts = append(facts, f) - // } - // if emailSearchStr != "" { - // f, err := fact.NewFact(fact.Email, emailSearchStr) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new fact: %+v", err) - // } - // facts = append(facts, f) - // } - // if phoneSearchStr != "" { - // f, err := fact.NewFact(fact.Phone, phoneSearchStr) - // if err != nil { - // jww.FATAL.Panicf("Failed to create new fact: %+v", err) - // } - // facts = append(facts, f) - // } - - // userToRemove := viper.GetString("remove") - // if userToRemove != "" { - // f, err := fact.NewFact(fact.Username, userToRemove) - // if err != nil { - // jww.FATAL.Panicf( - // "Failed to create new fact: %+v", err) - // } - // err = userDiscoveryMgr.RemoveUser(f) - // if err != nil { - // fmt.Printf("Couldn't remove user %s\n", - // userToRemove) - // jww.FATAL.Panicf( - // "Failed to remove user %s: %+v", - // userToRemove, err) - // } - // fmt.Printf("Removed user from discovery: %s\n", - // userToRemove) - // } - - // if len(facts) == 0 { - // err = client.StopNetworkFollower() - // if err != nil { - // jww.WARN.Print(err) - // } - // return - // } - - // err = userDiscoveryMgr.Search(facts, - // func(contacts []contact.Contact, err error) { - // if err != nil { - // jww.FATAL.Panicf("%+v", err) - // } - // for _, c := range contacts { - // printContact(c) - // } - // }, 90*time.Second) - // if err != nil { - // jww.FATAL.Panicf("%+v", err) - // } - - // time.Sleep(91 * time.Second) - // err = client.StopNetworkFollower() - // if err != nil { - // jww.WARN.Print(err) - // } + err := client.StartNetworkFollower(50 * time.Millisecond) + if err != nil { + jww.FATAL.Panicf("%+v", err) + } + + // Wait until connected or crash on timeout + connected := make(chan bool, 10) + client.GetNetworkInterface().AddHealthCallback( + func(isconnected bool) { + connected <- isconnected + }) + waitUntilConnected(connected) + + // Make user discovery manager + stream := client.GetRng().GetStream() + defer stream.Close() + userToRegister := viper.GetString("register") + userDiscoveryMgr, err := ud.NewManager(client.GetNetworkInterface(), + client.GetE2EHandler(), client.NetworkFollowerStatus, + client.GetEventReporter(), + client.GetComms(), client.GetStorage(), + stream, + userToRegister, client.GetStorage().GetKV()) + if err != nil { + if strings.Contains(err.Error(), ud.IsRegisteredErr) { + userDiscoveryMgr, err = ud.LoadManager(client.GetNetworkInterface(), + client.GetE2EHandler(), client.GetEventReporter(), + client.GetComms(), + client.GetStorage(), client.GetStorage().GetKV()) + if err != nil { + jww.FATAL.Panicf("Failed to load UD manager: %+v", err) + } + } else { + jww.FATAL.Panicf("Failed to create new UD manager: %+v", err) + + } + } + + var newFacts fact.FactList + phone := viper.GetString("addphone") + if phone != "" { + f, err := fact.NewFact(fact.Phone, phone) + if err != nil { + jww.FATAL.Panicf("Failed to create new fact: %+v", err) + } + newFacts = append(newFacts, f) + } + + email := viper.GetString("addemail") + if email != "" { + f, err := fact.NewFact(fact.Email, email) + if err != nil { + jww.FATAL.Panicf("Failed to create new fact: %+v", err) + } + newFacts = append(newFacts, f) + } + + for i := 0; i < len(newFacts); i++ { + r, err := userDiscoveryMgr.SendRegisterFact(newFacts[i]) + if err != nil { + fmt.Printf("Failed to register fact: %s\n", + newFacts[i]) + jww.FATAL.Panicf("Failed to send register fact: %+v", err) + } + // TODO Store the code? + jww.INFO.Printf("Fact Add Response: %+v", r) + } + + confirmID := viper.GetString("confirm") + if confirmID != "" { + err = userDiscoveryMgr.ConfirmFact(confirmID, confirmID) + if err != nil { + fmt.Printf("Couldn't confirm fact: %s\n", + err.Error()) + jww.FATAL.Panicf("%+v", err) + } + } + + udContact, err := userDiscoveryMgr.GetContact() + if err != nil { + fmt.Printf("Failed to get user discovery contact object: %+v", err) + jww.FATAL.Printf("Failed to get user discovery contact object: %+v", err) + } + + // Handle lookup (verification) process + // Note: Cryptographic verification occurs above the bindings layer + lookupIDStr := viper.GetString("lookup") + if lookupIDStr != "" { + lookupID, _ := parseRecipient(lookupIDStr) + //if !ok { + // jww.FATAL.Panicf("Could not parse recipient: %s", lookupIDStr) + //} + + cb := func(newContact contact.Contact, err error) { + if err != nil { + jww.FATAL.Panicf("UserDiscovery Lookup error: %+v", err) + } + printContact(newContact) + } + _, _, err = ud.Lookup(client.GetNetworkInterface(), + stream, client.GetE2EHandler().GetGroup(), + udContact, cb, lookupID, single.GetDefaultRequestParams()) + if err != nil { + jww.WARN.Printf("Failed UD lookup: %+v", err) + } + + time.Sleep(31 * time.Second) + } + + if viper.GetString("batchadd") != "" { + idListFile, err := utils.ReadFile(viper.GetString("batchadd")) + if err != nil { + fmt.Printf("BATCHADD: Couldn't read file: %s\n", + err.Error()) + jww.FATAL.Panicf("BATCHADD: Couldn't read file: %+v", err) + } + restored, _, _, err := xxmutils.RestoreContactsFromBackup( + idListFile, client, userDiscoveryMgr, nil) + if err != nil { + jww.FATAL.Panicf("%+v", err) + } + for i := 0; i < len(restored); i++ { + uid := restored[i] + for !client.HasAuthenticatedChannel(uid) { + time.Sleep(time.Second) + } + jww.INFO.Printf("Authenticated channel established for %s", uid) + } + } + usernameSearchStr := viper.GetString("searchusername") + emailSearchStr := viper.GetString("searchemail") + phoneSearchStr := viper.GetString("searchphone") + + var facts fact.FactList + if usernameSearchStr != "" { + f, err := fact.NewFact(fact.Username, usernameSearchStr) + if err != nil { + jww.FATAL.Panicf("Failed to create new fact: %+v", err) + } + facts = append(facts, f) + } + if emailSearchStr != "" { + f, err := fact.NewFact(fact.Email, emailSearchStr) + if err != nil { + jww.FATAL.Panicf("Failed to create new fact: %+v", err) + } + facts = append(facts, f) + } + if phoneSearchStr != "" { + f, err := fact.NewFact(fact.Phone, phoneSearchStr) + if err != nil { + jww.FATAL.Panicf("Failed to create new fact: %+v", err) + } + facts = append(facts, f) + } + + userToRemove := viper.GetString("remove") + if userToRemove != "" { + f, err := fact.NewFact(fact.Username, userToRemove) + if err != nil { + jww.FATAL.Panicf( + "Failed to create new fact: %+v", err) + } + err = userDiscoveryMgr.PermanentDeleteAccount(f) + if err != nil { + fmt.Printf("Couldn't remove user %s\n", + userToRemove) + jww.FATAL.Panicf( + "Failed to remove user %s: %+v", + userToRemove, err) + } + fmt.Printf("Removed user from discovery: %s\n", + userToRemove) + } + + if len(facts) == 0 { + err = client.StopNetworkFollower() + if err != nil { + jww.WARN.Print(err) + } + return + } + + cb := func(contacts []contact.Contact, err error) { + if err != nil { + jww.FATAL.Panicf("%+v", err) + } + for _, c := range contacts { + printContact(c) + } + } + + _, _, err = ud.Search(client.GetNetworkInterface(), + client.GetEventReporter(), + stream, client.GetE2EHandler().GetGroup(), + udContact, cb, facts, single.GetDefaultRequestParams()) + if err != nil { + jww.FATAL.Panicf("%+v", err) + } + + time.Sleep(91 * time.Second) + err = client.StopNetworkFollower() + if err != nil { + jww.WARN.Print(err) + } }, } diff --git a/cmix/remoteFilters.go b/cmix/remoteFilters.go index 45afbd1a3d1ae7cecbb57a6d47cda17af34f3ba8..37cf100e60396c612df73e85b31e5d07c5688d2f 100644 --- a/cmix/remoteFilters.go +++ b/cmix/remoteFilters.go @@ -25,10 +25,10 @@ func NewRemoteFilter(data *mixmessages.ClientBloom) *RemoteFilter { type RemoteFilter struct { data *mixmessages.ClientBloom - filter *bloom.Ring + filter *bloom.Bloom } -func (rf *RemoteFilter) GetFilter() *bloom.Ring { +func (rf *RemoteFilter) GetFilter() *bloom.Bloom { if rf.filter == nil { var err error diff --git a/go.mod b/go.mod index 412d59c59862e11e2ea681e4b3048c8c49f0ade2..5cc7bdbc98c27ad9aad0f873ef32a516cc24c9f8 100644 --- a/go.mod +++ b/go.mod @@ -11,7 +11,7 @@ require ( github.com/spf13/cobra v1.1.1 github.com/spf13/jwalterweatherman v1.1.0 github.com/spf13/viper v1.7.1 - gitlab.com/elixxir/bloomfilter v0.0.0-20200930191214-10e9ac31b228 + gitlab.com/elixxir/bloomfilter v0.0.0-20211222005329-7d931ceead6f gitlab.com/elixxir/comms v0.0.4-0.20220323190139-9ed75f3a8b2c gitlab.com/elixxir/crypto v0.0.7-0.20220425192911-a23209a58073 gitlab.com/elixxir/ekv v0.1.7 diff --git a/go.sum b/go.sum index 449abdbda8c4778ece9f8de9852071e33cf18f92..b2b24d4d75babae71f71578a773220de0cf06b99 100644 --- a/go.sum +++ b/go.sum @@ -274,6 +274,8 @@ github.com/zeebo/pcg v1.0.0 h1:dt+dx+HvX8g7Un32rY9XWoYnd0NmKmrIzpHF7qiTDj0= github.com/zeebo/pcg v1.0.0/go.mod h1:09F0S9iiKrwn9rlI5yjLkmrug154/YRW6KnnXVDM/l4= gitlab.com/elixxir/bloomfilter v0.0.0-20200930191214-10e9ac31b228 h1:Gi6rj4mAlK0BJIk1HIzBVMjWNjIUfstrsXC2VqLYPcA= gitlab.com/elixxir/bloomfilter v0.0.0-20200930191214-10e9ac31b228/go.mod h1:H6jztdm0k+wEV2QGK/KYA+MY9nj9Zzatux/qIvDDv3k= +gitlab.com/elixxir/bloomfilter v0.0.0-20211222005329-7d931ceead6f h1:yXGvNBqzZwAhDYlSnxPRbgor6JWoOt1Z7s3z1O9JR40= +gitlab.com/elixxir/bloomfilter v0.0.0-20211222005329-7d931ceead6f/go.mod h1:H6jztdm0k+wEV2QGK/KYA+MY9nj9Zzatux/qIvDDv3k= gitlab.com/elixxir/comms v0.0.4-0.20220308183624-c2183e687a03 h1:4eNjO3wCyHgxpGeq2zgDb5SsdTcQaG5IZjBOuEL6KgM= gitlab.com/elixxir/comms v0.0.4-0.20220308183624-c2183e687a03/go.mod h1:4yMdU+Jee5W9lqkZGHJAuipEhW7FloT0eyVEFUJza+E= gitlab.com/elixxir/comms v0.0.4-0.20220323190139-9ed75f3a8b2c h1:ajjTw08YjRjl3HvtBNGtoCWhOg8k8upqmTweH18wkC4= @@ -283,6 +285,8 @@ gitlab.com/elixxir/crypto v0.0.3/go.mod h1:ZNgBOblhYToR4m8tj4cMvJ9UsJAUKq+p0gCp0 gitlab.com/elixxir/crypto v0.0.7-0.20220222221347-95c7ae58da6b/go.mod h1:tD6XjtQh87T2nKZL5I/pYPck5M2wLpkZ1Oz7H/LqO10= gitlab.com/elixxir/crypto v0.0.7-0.20220309234716-1ba339865787 h1:+qmsWov412+Yn7AKUhTbOcDgAydNXlNLPmFpO2W5LwY= gitlab.com/elixxir/crypto v0.0.7-0.20220309234716-1ba339865787/go.mod h1:tD6XjtQh87T2nKZL5I/pYPck5M2wLpkZ1Oz7H/LqO10= +gitlab.com/elixxir/crypto v0.0.7-0.20220317172048-3de167bd9406 h1:PRA8OJMXuy9JZmUuZ442AIE/tWY7HisqezyLNhpZZ9w= +gitlab.com/elixxir/crypto v0.0.7-0.20220317172048-3de167bd9406/go.mod h1:tD6XjtQh87T2nKZL5I/pYPck5M2wLpkZ1Oz7H/LqO10= gitlab.com/elixxir/crypto v0.0.7-0.20220325215559-7489d68d7714 h1:epnov8zyFWod14MUNtGHSbZCVSkZjN4NvoiBs1TgEV8= gitlab.com/elixxir/crypto v0.0.7-0.20220325215559-7489d68d7714/go.mod h1:tD6XjtQh87T2nKZL5I/pYPck5M2wLpkZ1Oz7H/LqO10= gitlab.com/elixxir/crypto v0.0.7-0.20220325224306-705ce59288bb h1:WdlmG+KPaM2Pjo1EFiFFPYEVSMV64Di1CitQnXGWBOQ= diff --git a/interfaces/networkManager.go b/interfaces/networkManager.go index 1315c7d710571d694f6ca77d7b0222e2e50aa0f9..2139e9597c6a4cdc51714e47308d6aa91d3481c5 100644 --- a/interfaces/networkManager.go +++ b/interfaces/networkManager.go @@ -50,7 +50,7 @@ type NetworkManager interface { id.Round, []ephemeral.Id, error) /*===Message Reception================================================*/ - /* Identities are all network identites which the client is currently + /* Identities are all network identities which the client is currently trying to pick up message on. An identity must be added to receive messages, fake ones will be used to poll the network if none are present. On creation of the network handler, the identity in @@ -132,7 +132,7 @@ type NetworkManager interface { // the given identity DeleteClientTriggers(identity *id.ID) - // TrackTriggers - Registers a callback which will get called + // TrackServices - Registers a callback which will get called // every time triggers change. // It will receive the triggers list every time it is modified. // Will only get callbacks while the Network Follower is running. @@ -163,7 +163,8 @@ type NetworkManager interface { // relationship with NumRegisteredNodes() int - // Triggers the generation of a keying relationship with a given node + // TriggerNodeRegistration triggers the generation of a keying + // relationship with a given node TriggerNodeRegistration(nid *id.ID) /*===Historical Rounds================================================*/ @@ -176,7 +177,7 @@ type NetworkManager interface { // network LookupHistoricalRound(rid id.Round, callback func(info *mixmessages.RoundInfo, - success bool)) error + success bool)) error /*===Sender===========================================================*/ /* The sender handles sending comms to the network. It tracks diff --git a/single/request.go b/single/request.go index 6f2d71ae8183a3f45f0f6dde7edaff80d104fc29..6cb079652cca7e72a82c2c1f623802a5ff19f64a 100644 --- a/single/request.go +++ b/single/request.go @@ -212,8 +212,6 @@ func TransmitRequest(recipient contact.Contact, tag string, payload []byte, errors.Errorf(errSendRequest, tag, recipient, err) } - // todo: this is jono's work but there's a send above it, - // probably just WIP code, talk to jono and resolve once tests work roundIDs := make([]id.Round, len(parts)+1) roundIDs[0] = rid for i, part := range parts { diff --git a/storage/user/cryptographic.go b/storage/user/cryptographic.go index 592fc9c2322d3f8552d3e0ebc5f721cd292ed384..fd4b73047008f6f0f78ad9a2f1b067372932aae6 100644 --- a/storage/user/cryptographic.go +++ b/storage/user/cryptographic.go @@ -41,7 +41,9 @@ type ciDisk struct { IsPrecanned bool } -func newCryptographicIdentity(transmissionID, receptionID *id.ID, transmissionSalt, receptionSalt []byte, transmissionRsa, receptionRsa *rsa.PrivateKey, +func newCryptographicIdentity(transmissionID, receptionID *id.ID, + transmissionSalt, receptionSalt []byte, + transmissionRsa, receptionRsa *rsa.PrivateKey, isPrecanned bool, kv *versioned.KV) *CryptographicIdentity { ci := &CryptographicIdentity{ diff --git a/ud/interfaces.go b/ud/interfaces.go index 6042ae755fd34b770a3dcf503768d76346ebf50c..ba5bff8b7eb20cd55da1a1f9c7cf91d3478d8df1 100644 --- a/ud/interfaces.go +++ b/ud/interfaces.go @@ -24,6 +24,10 @@ type E2E interface { // GetReceptionID returns the default IDs GetReceptionID() *id.ID + + // GetHistoricalDHPubkey returns the user's Historical DH + // Public Key + GetHistoricalDHPubkey() *cyclic.Int } // UserInfo is a sub-interface for the user.User object in storage. diff --git a/ud/manager.go b/ud/manager.go index 53e6a37f62630e24f0754ac4b731bddf01e37c0c..9d60515e5995059eb4926e6ef33384a69e6a0347 100644 --- a/ud/manager.go +++ b/ud/manager.go @@ -17,6 +17,12 @@ import ( "time" ) +const ( + IsRegisteredErr = "NewManager is already registered. " + + "NewManager is meant for the first instantiation. Use LoadManager " + + "for all other calls" +) + // Manager is the control structure for the contacting the user discovery service. type Manager struct { // Network is a sub-interface of the cmix.Client interface. It @@ -85,6 +91,10 @@ func NewManager(services CMix, e2e E2E, kv: kv, } + if m.isRegistered() { + return nil, errors.Errorf(IsRegisteredErr) + } + // Initialize store var err error m.store, err = store.NewOrLoadStore(kv) diff --git a/ud/register.go b/ud/register.go index caae813dc950dbe260a07b19ce5be12b6a5db2e7..3df8edd643216d8629e7c074152cd23f7ef2cc04 100644 --- a/ud/register.go +++ b/ud/register.go @@ -25,7 +25,7 @@ func (m *Manager) register(username string, rng csprng.Source, RSAPublicPem: string(rsa.CreatePublicKeyPem(cryptoUser.ReceptionRSA.GetPublic())), IdentityRegistration: &pb.Identity{ Username: username, - DhPubKey: cryptoUser.E2eDhPublicKey.Bytes(), + DhPubKey: m.e2e.GetHistoricalDHPubkey().Bytes(), Salt: cryptoUser.ReceptionSalt, }, UID: cryptoUser.ReceptionID.Marshal(), diff --git a/ud/search.go b/ud/search.go index d432f47561b079ffecb335c9b999d07561a1cb7e..7061f4cc3a5c0b1c463b665a06f7cc9b3d70bdaf 100644 --- a/ud/search.go +++ b/ud/search.go @@ -54,7 +54,8 @@ func Search(services CMix, events event.Reporter, factMap: factMap, } - rndId, ephId, err := single.TransmitRequest(udContact, SearchTag, requestMarshaled, + rndId, ephId, err := single.TransmitRequest(udContact, SearchTag, + requestMarshaled, response, params, services, rng, grp) if err != nil { return []id.Round{}, receptionID.EphemeralIdentity{}, diff --git a/xxmutils/restoreContacts.go b/xxmutils/restoreContacts.go index 6b8afad7073c5d9ff7b4ad56e19515bdd596440c..69a09d2e6258479cfdc3a08aaeca050442fdc256 100644 --- a/xxmutils/restoreContacts.go +++ b/xxmutils/restoreContacts.go @@ -11,6 +11,7 @@ import ( "encoding/json" "errors" "fmt" + "gitlab.com/elixxir/client/single" "gitlab.com/xx_network/primitives/netTime" "math" "strings" @@ -41,6 +42,11 @@ func RestoreContactsFromBackup(backupPartnerIDs []byte, client *api.Client, updatesCb interfaces.RestoreContactsUpdater) ([]*id.ID, []*id.ID, []error, error) { + udContact, err := udManager.GetContact() + if err != nil { + return nil, nil, nil, err + } + var restored, failed []*id.ID var errs []error @@ -93,7 +99,7 @@ func RestoreContactsFromBackup(backupPartnerIDs []byte, client *api.Client, rsWg := &sync.WaitGroup{} rsWg.Add(numRoutines) for i := 0; i < numRoutines; i++ { - go LookupContacts(lookupCh, foundCh, failCh, udManager, lcWg) + go LookupContacts(lookupCh, foundCh, failCh, client, udContact, lcWg) go ResetSessions(resetContactCh, restoredCh, failCh, *client, rsWg) } @@ -125,7 +131,6 @@ func RestoreContactsFromBackup(backupPartnerIDs []byte, client *api.Client, // Event Processing done := false - var err error = nil for !done { // NOTE: Timer is reset every loop timeoutTimer := time.NewTimer(restoreTimeout) @@ -173,13 +178,13 @@ func RestoreContactsFromBackup(backupPartnerIDs []byte, client *api.Client, // the mobile phone apps and are not intended to be part of the xxDK. It // should be treated as internal functions specific to the phone apps. func LookupContacts(in chan *id.ID, out chan *contact.Contact, - failCh chan failure, udManager *ud.Manager, + failCh chan failure, client *api.Client, udContact contact.Contact, wg *sync.WaitGroup) { defer wg.Done() // Start looking up contacts with user discovery and feed this // contacts channel. for lookupID := range in { - c, err := LookupContact(lookupID, udManager) + c, err := LookupContact(lookupID, client, udContact) if err == nil { out <- c continue @@ -221,7 +226,7 @@ func ResetSessions(in, out chan *contact.Contact, failCh chan failure, // xxDK users should not use this function. This function is used by // the mobile phone apps and are not intended to be part of the xxDK. It // should be treated as internal functions specific to the phone apps. -func LookupContact(userID *id.ID, udManager *ud.Manager) ( +func LookupContact(userID *id.ID, client *api.Client, udContact contact.Contact) ( *contact.Contact, error) { // This is a little wonky, but wait until we get called then // set the result to the contact objects details if there is @@ -240,8 +245,10 @@ func LookupContact(userID *id.ID, udManager *ud.Manager) ( waiter.Lock() // in MS, so 90 seconds - timeout := time.Duration(90 * time.Second) - udManager.Lookup(userID, lookupCB, timeout) + stream := client.GetRng().GetStream() + defer stream.Close() + _, _, err = ud.Lookup(client.GetNetworkInterface(), stream, client.GetE2EHandler().GetGroup(), + udContact, lookupCB, userID, single.GetDefaultRequestParams()) // Now force a wait for callback to exit waiter.Lock() @@ -272,7 +279,7 @@ type failure struct { const stateStoreFmt = "restoreContactsFromBackup/v1/%s" type stateStore struct { - apiStore *storage.Session + apiStore storage.Session // TODO: We could put a syncmap or something here instead of // 1-key-per-id }