Skip to content
Snippets Groups Projects
Commit b1dcde08 authored by Jono Wenger's avatar Jono Wenger
Browse files

Add nonce to message and add nonce generation during construction

parent 05252271
No related branches found
No related tags found
5 merge requests!510Release,!419rewrote the health tracker to both consider if there are waiting rounds and...,!400Add nonce to message and add nonce generation during construction,!397Fully Decentralized channels,!340Project/channels
......@@ -47,6 +47,10 @@ type ChannelMessage struct {
// nickname is the name which the user is using for this message
// it will not be longer than 24 characters
Nickname string `protobuf:"bytes,5,opt,name=Nickname,proto3" json:"Nickname,omitempty"`
// Nonce is 32 bits of randomness to ensure that two messages in the same
// round with that have the same nickname, payload, and lease will not have
// the same message ID.
Nonce []byte `protobuf:"bytes,6,opt,name=Nonce,proto3" json:"Nonce,omitempty"`
}
func (x *ChannelMessage) Reset() {
......@@ -116,6 +120,13 @@ func (x *ChannelMessage) GetNickname() string {
return ""
}
func (x *ChannelMessage) GetNonce() []byte {
if x != nil {
return x.Nonce
}
return nil
}
// UserMessage is a message sent by a user who is a member within the channel.
type UserMessage struct {
state protoimpl.MessageState
......@@ -194,7 +205,7 @@ var File_channelMessages_proto protoreflect.FileDescriptor
var file_channelMessages_proto_rawDesc = []byte{
0x0a, 0x15, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65,
0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x08, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c,
0x73, 0x22, 0x98, 0x01, 0x0a, 0x0e, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x4d, 0x65, 0x73,
0x73, 0x22, 0xae, 0x01, 0x0a, 0x0e, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x4d, 0x65, 0x73,
0x73, 0x61, 0x67, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x4c, 0x65, 0x61, 0x73, 0x65, 0x18, 0x01, 0x20,
0x01, 0x28, 0x03, 0x52, 0x05, 0x4c, 0x65, 0x61, 0x73, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x52, 0x6f,
0x75, 0x6e, 0x64, 0x49, 0x44, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x52, 0x07, 0x52, 0x6f, 0x75,
......@@ -203,17 +214,18 @@ var file_channelMessages_proto_rawDesc = []byte{
0x61, 0x64, 0x54, 0x79, 0x70, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x50, 0x61, 0x79, 0x6c, 0x6f, 0x61,
0x64, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x07, 0x50, 0x61, 0x79, 0x6c, 0x6f, 0x61, 0x64,
0x12, 0x1a, 0x0a, 0x08, 0x4e, 0x69, 0x63, 0x6b, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x05, 0x20, 0x01,
0x28, 0x09, 0x52, 0x08, 0x4e, 0x69, 0x63, 0x6b, 0x6e, 0x61, 0x6d, 0x65, 0x22, 0x69, 0x0a, 0x0b,
0x55, 0x73, 0x65, 0x72, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x4d,
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x07, 0x4d, 0x65,
0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75,
0x72, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x74,
0x75, 0x72, 0x65, 0x12, 0x22, 0x0a, 0x0c, 0x45, 0x43, 0x43, 0x50, 0x75, 0x62, 0x6c, 0x69, 0x63,
0x4b, 0x65, 0x79, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x0c, 0x45, 0x43, 0x43, 0x50, 0x75,
0x62, 0x6c, 0x69, 0x63, 0x4b, 0x65, 0x79, 0x42, 0x24, 0x5a, 0x22, 0x67, 0x69, 0x74, 0x6c, 0x61,
0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x65, 0x6c, 0x69, 0x78, 0x78, 0x69, 0x72, 0x2f, 0x63, 0x6c,
0x69, 0x65, 0x6e, 0x74, 0x2f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x73, 0x62, 0x06, 0x70,
0x72, 0x6f, 0x74, 0x6f, 0x33,
0x28, 0x09, 0x52, 0x08, 0x4e, 0x69, 0x63, 0x6b, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x14, 0x0a, 0x05,
0x4e, 0x6f, 0x6e, 0x63, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x4e, 0x6f, 0x6e,
0x63, 0x65, 0x22, 0x69, 0x0a, 0x0b, 0x55, 0x73, 0x65, 0x72, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67,
0x65, 0x12, 0x18, 0x0a, 0x07, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x18, 0x01, 0x20, 0x01,
0x28, 0x0c, 0x52, 0x07, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x53,
0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09,
0x53, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x22, 0x0a, 0x0c, 0x45, 0x43, 0x43,
0x50, 0x75, 0x62, 0x6c, 0x69, 0x63, 0x4b, 0x65, 0x79, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0c, 0x52,
0x0c, 0x45, 0x43, 0x43, 0x50, 0x75, 0x62, 0x6c, 0x69, 0x63, 0x4b, 0x65, 0x79, 0x42, 0x24, 0x5a,
0x22, 0x67, 0x69, 0x74, 0x6c, 0x61, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x65, 0x6c, 0x69, 0x78,
0x78, 0x69, 0x72, 0x2f, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x2f, 0x63, 0x68, 0x61, 0x6e, 0x6e,
0x65, 0x6c, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
}
var (
......
......@@ -32,9 +32,9 @@ message ChannelMessage{
// it will not be longer than 24 characters
string Nickname = 5;
// Nonce is 32 bits of randomness to ensure that in the event that in the
// same round two messages are send with the same nickname, payload,
// and lease, they will not have the same message ID.
// Nonce is 32 bits of randomness to ensure that two messages in the same
// round with that have the same nickname, payload, and lease will not have
// the same message ID.
bytes Nonce = 6;
}
......
......@@ -9,6 +9,7 @@ package channels
import (
"crypto/ed25519"
"github.com/pkg/errors"
"gitlab.com/elixxir/client/cmix"
"gitlab.com/elixxir/client/cmix/rounds"
cryptoChannel "gitlab.com/elixxir/crypto/channel"
......@@ -24,6 +25,9 @@ const (
cmixChannelReactionVersion = 0
)
// The size of the nonce used in the message ID.
const messageNonceSize = 4
// SendGeneric is used to send a raw message over a channel. In general, it
// should be wrapped in a function which defines the wire protocol
// If the final message, before being sent over the wire, is too long, this will
......@@ -49,6 +53,21 @@ func (m *manager) SendGeneric(channelID *id.ID, messageType MessageType,
PayloadType: uint32(messageType),
Payload: msg,
Nickname: nickname,
Nonce: make([]byte, messageNonceSize),
}
// Generate random nonce to be used for message ID generation. This makes it
// so two identical messages sent on the same round have different message IDs
rng := m.rng.GetStream()
n, err := rng.Read(chMsg.Nonce)
rng.Close()
if err != nil {
return cryptoChannel.MessageID{}, rounds.Round{}, ephemeral.Id{},
errors.Errorf("Failed to generate nonce: %+v", err)
} else if n != messageNonceSize {
return cryptoChannel.MessageID{}, rounds.Round{}, ephemeral.Id{},
errors.Errorf(
"Generated %d bytes for %-byte nonce", n, messageNonceSize)
}
usrMsg := &UserMessage{
......@@ -124,8 +143,24 @@ func (m *manager) SendAdminGeneric(privKey rsa.PrivateKey, channelID *id.ID,
PayloadType: uint32(messageType),
Payload: msg,
Nickname: AdminUsername,
Nonce: make([]byte, messageNonceSize),
}
//Note: we are not checking check if message is too long before trying to
// Generate random nonce to be used for message ID generation. This makes it
// so two identical messages sent on the same round have different message IDs
rng := m.rng.GetStream()
n, err := rng.Read(chMsg.Nonce)
rng.Close()
if err != nil {
return cryptoChannel.MessageID{}, rounds.Round{}, ephemeral.Id{},
errors.Errorf("Failed to generate nonce: %+v", err)
} else if n != messageNonceSize {
return cryptoChannel.MessageID{}, rounds.Round{}, ephemeral.Id{},
errors.Errorf(
"Generated %d bytes for %-byte nonce", n, messageNonceSize)
}
// Note: we are not checking if message is too long before trying to
// find a round
//Build the function pointer that will build the message
......
......@@ -15,11 +15,13 @@ import (
"gitlab.com/elixxir/client/cmix/rounds"
"gitlab.com/elixxir/client/storage/versioned"
cryptoChannel "gitlab.com/elixxir/crypto/channel"
"gitlab.com/elixxir/crypto/fastRNG"
"gitlab.com/elixxir/crypto/rsa"
"gitlab.com/elixxir/ekv"
"gitlab.com/xx_network/crypto/csprng"
"gitlab.com/xx_network/primitives/netTime"
"math/rand"
"sync"
"testing"
"time"
......@@ -153,6 +155,8 @@ func TestSendGeneric(t *testing.T) {
m := &manager{
me: pi,
channels: make(map[id.ID]*joinedChannel),
mux: sync.RWMutex{},
rng: fastRNG.NewStreamGenerator(1000, 10, csprng.NewSystemRNG),
nicknameManager: &nicknameManager{
byChannel: make(map[id.ID]string),
kv: nil,
......@@ -243,6 +247,7 @@ func TestAdminGeneric(t *testing.T) {
kv: nil,
},
me: pi,
rng: fastRNG.NewStreamGenerator(1000, 10, csprng.NewSystemRNG),
st: loadSendTracker(&mockBroadcastClient{},
versioned.NewKV(ekv.MakeMemstore()), func(chID *id.ID,
umi *userMessageInternal, ts time.Time,
......@@ -332,6 +337,7 @@ func TestSendMessage(t *testing.T) {
byChannel: make(map[id.ID]string),
kv: nil,
},
rng: fastRNG.NewStreamGenerator(1000, 10, csprng.NewSystemRNG),
st: loadSendTracker(&mockBroadcastClient{},
versioned.NewKV(ekv.MakeMemstore()), func(chID *id.ID,
umi *userMessageInternal, ts time.Time,
......@@ -426,6 +432,7 @@ func TestSendReply(t *testing.T) {
byChannel: make(map[id.ID]string),
kv: nil,
},
rng: fastRNG.NewStreamGenerator(1000, 10, csprng.NewSystemRNG),
st: loadSendTracker(&mockBroadcastClient{},
versioned.NewKV(ekv.MakeMemstore()), func(chID *id.ID,
umi *userMessageInternal, ts time.Time,
......@@ -519,6 +526,7 @@ func TestSendReaction(t *testing.T) {
byChannel: make(map[id.ID]string),
kv: nil,
},
rng: fastRNG.NewStreamGenerator(1000, 10, csprng.NewSystemRNG),
channels: make(map[id.ID]*joinedChannel),
st: loadSendTracker(&mockBroadcastClient{},
versioned.NewKV(ekv.MakeMemstore()), func(chID *id.ID,
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment