cmix

package
v4.7.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Dec 19, 2023 License: BSD-2-Clause, BSD-2-Clause Imports: 51 Imported by: 1

Documentation

Index

Constants

View Source
const BloomFilterHashes = 10
View Source
const BloomFilterSize = 648 // In Bits
View Source
const DefaultDebugTag = "External"
View Source
const DefaultFollowPeriod = 1000 * time.Millisecond

DefaultFollowPeriod is the default period in which the network will be polled for state changes (see [Client.Follow]).

Variables

This section is empty.

Functions

func Checker

func Checker(roundID id.Round, filters []*RemoteFilter, cr *store.CheckedRounds) bool

Checker is a single use function that is meant to be wrapped and adhere to the knownRounds checker interface. It receives a round ID and looks up the state of that round to determine if the client has a message waiting in it. It will return true if it can conclusively determine no message exists, and it will return false and set the round to processing if it needs further investigation. Once it determines messages might be waiting in a round, it determines if the information about that round is already present. If it is, then the data is sent to Message Retrieval Workers; otherwise, it is sent to Historical Round Retrieval false: no message true: message

func TrackResults

func TrackResults(resultsCh chan ds.EventReturn, numResults int) (bool, int, int)

TrackResults follows the results of events. It returns true if the collection of events resolved well, and then a count of how many rounds failed and how many roundEvents timed out.

Types

type CMIXParams

type CMIXParams struct {
	// RoundTries is the maximum number of rounds to try to send on
	RoundTries     uint
	Timeout        time.Duration
	RetryDelay     time.Duration
	ExcludedRounds excludedRounds.ExcludedRounds `json:"-"`

	// SendTimeout is the duration to wait before sending on a round times out
	// and a new round is tried.
	SendTimeout time.Duration

	// DebugTag is a tag that is printed with sending logs to help localize the
	// source. All internal sends are tagged, so the default tag is "External".
	DebugTag string

	// Stop can be used to stop the send early.
	Stop *stoppable.Single `json:"-"`

	// BlacklistedNodes is a list of nodes to not send to; will skip a round
	// with these nodes in it.
	BlacklistedNodes NodeMap

	// Critical indicates if the message is critical. The system will track that
	// the round it sends on completes and will auto resend in the event the
	// round fails or completion cannot be determined. The sent data will be
	// byte identical, so this has a high chance of metadata leak. This system
	// should only be used in cases where repeats cannot be different. Only used
	// in sendCmix, not sendManyCmix.
	Critical bool

	// Probe tells the client that this send can be used to test network performance,
	// that outgoing latency is not important
	Probe bool
}

func GetCMIXParameters

func GetCMIXParameters(params string) (CMIXParams, error)

GetCMIXParameters obtains default CMIX parameters, or overrides with given parameters if set.

func GetDefaultCMIXParams

func GetDefaultCMIXParams() CMIXParams

func (CMIXParams) MarshalJSON

func (p CMIXParams) MarshalJSON() ([]byte, error)

MarshalJSON adheres to the json.Marshaler interface.

func (CMIXParams) SetDebugTag

func (p CMIXParams) SetDebugTag(newTag string) CMIXParams

SetDebugTag appends the debug tag if one already exists, otherwise it just used the new debug tag

func (*CMIXParams) UnmarshalJSON

func (p *CMIXParams) UnmarshalJSON(data []byte) error

UnmarshalJSON adheres to the json.Unmarshaler interface.

type Client

type Client interface {
	// Follow starts the tracking of the network in a new thread.
	// Errors that occur are reported on the ClientErrorReport function if
	// passed. The returned stoppable can be used to stop the follower.
	// Only one follower may run at a time.
	Follow(report ClientErrorReport) (stoppable.Stoppable, error)

	// SetTrackNetworkPeriod allows changing the frequency that follower threads
	// are started.
	//
	// Note that the frequency of the follower threads affect the power usage
	// of the device following the network.
	//   - Low period -> Higher frequency of polling -> Higher battery usage
	//   - High period -> Lower frequency of polling -> Lower battery usage
	// This may be used to enable a low power (or battery optimization) mode
	// for the end user.
	SetTrackNetworkPeriod(d time.Duration)

	// GetMaxMessageLength returns the max message size for the current network.
	GetMaxMessageLength() int

	// Send sends a "raw" cMix message payload to the provided recipient.
	// Returns the round ID of the round the payload was sent or an error if it
	// fails.
	// This does not have end-to-end encryption on it and is used exclusively as
	// a send for higher order cryptographic protocols. Do not use unless
	// implementing a protocol on top.
	//   recipient - cMix ID of the recipient.
	//   fingerprint - Key Fingerprint. 256-bit field to store a 255-bit
	//      fingerprint, the highest order bit must be 0 (panic otherwise). If your
	//      system does not use key fingerprints, this must be random bits.
	//   service - Reception Service. The backup way for a client to identify
	//    messages on receipt via trial hashing and to identify notifications.
	//      If unused, use message.GetRandomService to fill the field with
	//      random data.
	//   payload - Contents of the message. Cannot exceed the payload size for a
	//      cMix message (panic otherwise).
	//   mac - 256-bit field to store a 255-bit mac, highest order bit must be 0
	//      (panic otherwise). If used, fill with random bits.
	// Will return an error if the network is unhealthy or if it fails to send
	// (along with the reason). Blocks until successful sends or errors.
	// WARNING: Do not roll your own crypto.
	Send(recipient *id.ID, fingerprint format.Fingerprint,
		service Service, payload, mac []byte, cmixParams CMIXParams) (
		rounds.Round, ephemeral.Id, error)

	// SendMany sends many "raw" cMix message payloads to the provided
	// recipients all in the same round.
	// Returns the round ID of the round the payloads was sent or an error if it
	// fails.
	// This does not have end-to-end encryption on it and is used exclusively as
	// a send for higher order cryptographic protocols. Do not use unless
	// implementing a protocol on top.
	// Due to sending multiple payloads, this leaks more metadata than a
	// standard cMix send and should be in general avoided.
	//   recipient - cMix ID of the recipient.
	//   fingerprint - Key Fingerprint. 256-bit field to store a 255-bit
	//      fingerprint, highest order bit must be 0 (panic otherwise). If your
	//      system does not use key fingerprints, this must be random bits.
	//   service - Reception Service. The backup way for a client to identify
	//      messages on receipt via trial hashing and to identify notifications.
	//      If unused, use message.GetRandomService to fill the field with
	//      random data.
	//   payload - Contents of the message. Cannot exceed the payload size for a
	//      cMix message (panic otherwise).
	//   mac - 256-bit field to store a 255-bit mac, highest order bit must be 0
	//      (panic otherwise). If used, fill with random bits.
	// Will return an error if the network is unhealthy or if it fails to send
	// (along with the reason). Blocks until successful send or err.
	// WARNING: Do not roll your own crypto.
	SendMany(messages []TargetedCmixMessage,
		params CMIXParams) (rounds.Round, []ephemeral.Id, error)

	// SendWithAssembler sends a variable cmix payload to the provided recipient.
	// The payload sent is based on the Complier function passed in, which accepts
	// a round ID and returns the necessary payload data.
	// Returns the round ID of the round the payload was sent or an error if it
	// fails.
	// This does not have end-to-end encryption on it and is used exclusively as
	// a send for higher order cryptographic protocols. Do not use unless
	// implementing a protocol on top.
	//   recipient - cMix ID of the recipient.
	//   assembler - MessageAssembler function, accepting round ID and returning
	//   fingerprint
	//   format.Fingerprint, service message.Service, payload, mac []byte
	// Will return an error if the network is unhealthy or if it fails to send
	// (along with the reason). Blocks until successful sends or errors.
	// WARNING: Do not roll your own crypto.
	SendWithAssembler(recipient *id.ID, assembler MessageAssembler,
		cmixParams CMIXParams) (rounds.Round, ephemeral.Id, error)

	// SendManyWithAssembler sends variable cMix payloads to the provided recipients.
	// The payloads sent are based on the ManyMessageAssembler function passed in,
	// which accepts a round ID and returns the necessary payload data.
	// Returns the round IDs of the rounds the payloads were sent or an error if it
	// fails.
	// This does not have end-to-end encryption on it and is used exclusively as
	// a send operation for higher order cryptographic protocols. Do not use unless
	// implementing a protocol on top.
	//
	//	recipients - cMix IDs of the recipients.
	//	assembler - ManyMessageAssembler function, accepting round ID and returning
	// 	            a list of TargetedCmixMessage.
	//
	// Will return an error if the network is unhealthy or if it fails to send
	// (along with the reason). Blocks until successful sends or errors.
	// WARNING: Do not roll your own crypto.
	SendManyWithAssembler(recipients []*id.ID, assembler ManyMessageAssembler,
		params CMIXParams) (rounds.Round, []ephemeral.Id, error)

	// AddIdentity adds an identity to be tracked. If persistent is false,
	// the identity will not be stored to disk and will be dropped on reload.
	// If the fallthrough processor is not nil, it will be used to process
	// messages for this id in the event there isn't a service or fingerprint
	// that matches the message.
	//
	// validUntil is the time the identity self-destructs. To set for forever,
	// use identity.Forever.
	AddIdentity(id *id.ID, validUntil time.Time, persistent bool,
		fallthroughProcessor message.Processor)

	// AddIdentityWithHistory adds an identity to be tracked. If persistent is
	// false, the identity will not be stored to disk and will be dropped on
	// reload. It will pick up messages slowly back in the history or up back
	// until beginning or the start of message retention, which should be ~500
	// houses back.
	// If the fallthrough processor is not nil, it will be used to process
	// messages for this id in the event there isn't a service or fingerprint
	// that matches the message.
	AddIdentityWithHistory(id *id.ID, validUntil, beginning time.Time, persistent bool,
		fallthroughProcessor message.Processor)

	// RemoveIdentity removes a currently tracked identity.
	RemoveIdentity(id *id.ID)

	// GetIdentity returns a currently tracked identity.
	GetIdentity(get *id.ID) (identity.TrackedID, error)

	// AddFingerprint adds a fingerprint that will be handled by a specific
	// processor for messages received by the given identity. If a nil identity
	// is passed, it will automatically use the default identity in the session.
	AddFingerprint(identity *id.ID, fingerprint format.Fingerprint,
		mp message.Processor) error

	// DeleteFingerprint deletes a single fingerprint associated with the given
	// identity, if it exists. If a nil identity is passed, it will
	// automatically use the default identity in the session.
	DeleteFingerprint(identity *id.ID, fingerprint format.Fingerprint)

	// DeleteClientFingerprints deletes all fingerprint associated with the
	// given identity, if it exists. A specific identity must be supplied; a
	// nil identity will result in a panic.
	DeleteClientFingerprints(identity *id.ID)

	// AddService adds a service that can call a message handing function or be
	// used for notifications. In general, a single service can only be
	// registered for the same identifier/tag pair.
	//   preimage - The preimage that is triggered on.
	//   type - A descriptive string of the service. Generally used in
	//      notifications.
	//   source - A byte buffer of related data. Generally used in notifications.
	//     Example: Sender ID
	// There can be multiple "default" services; if the "default" tag is used,
	// then the identifier must be the client reception ID.
	// A service may have a nil response unless it is default. In general a
	// nil service is used to detect notifications when pickup is done by
	// fingerprints.
	AddService(clientID *id.ID, newService message.Service,
		response message.Processor)

	// UpsertCompressedService adds a compressed service which can call a message
	// handing function or be used for notifications. Online a single compressed
	// service can be registered to an identifier. If the same identifier is used,
	// it will replace the old one.
	UpsertCompressedService(clientID *id.ID, newService message.CompressedService,
		response message.Processor)

	// PauseNodeRegistrations stops all node registrations and returns a
	// function to resume them.
	PauseNodeRegistrations(timeout time.Duration) error

	// ChangeNumberOfNodeRegistrations changes the number of parallel node
	// registrations up to the initialized maximum.
	ChangeNumberOfNodeRegistrations(toRun int, timeout time.Duration) error

	// DeleteService deletes a message service. If only a single response is
	// associated with the preimage, the entire preimage is removed. If there is
	// more than one response, only the given response is removed. If nil is
	// passed in for response, all triggers for the preimage will be removed.
	// The processor is only used in deletion when deleting a default service
	DeleteService(clientID *id.ID, toDelete message.Service,
		processor message.Processor)

	// DeleteClientService deletes the mapping associated with an ID.
	// deletes both services and compressed services
	DeleteClientService(clientID *id.ID)

	// DeleteCompressedService - If only a single response is associated with the preimage,
	// the entire preimage is removed. If there is more than one response, only the
	// given response is removed. If nil is passed in for response, all triggers for
	// the preimage will be removed.
	DeleteCompressedService(clientID *id.ID, toDelete message.CompressedService,
		processor message.Processor)

	// TrackServices registers a callback that is called every time a service is
	// added or removed. It is also called once when registered. The callback
	// receives the new service lists every time they are modified. Callbacks
	// only occur when the network follower is running. Multiple
	// [message.ServicesTracker] can be registered.
	TrackServices(tracker message.ServicesTracker)

	// GetServices returns the current list of registered services and
	// compressed services. This returns the same lists as the last lists
	// provided to trackers registered with [TrackServices].
	GetServices() (message.ServiceList, message.CompressedServiceList)

	// CheckInProgressMessages retries processing all messages in check in
	// progress messages. Call this after adding fingerprints or triggers while
	// the follower is running.
	CheckInProgressMessages()

	// IsHealthy returns true if currently healthy.
	IsHealthy() bool

	// WasHealthy returns true if the network has ever been healthy in this run.
	WasHealthy() bool

	// AddHealthCallback adds a callback that gets called whenever the network
	// health changes. Returns a registration ID that can be used to unregister.
	AddHealthCallback(f func(bool)) uint64

	// RemoveHealthCallback removes a health callback using its registration ID.
	RemoveHealthCallback(uint64)

	// HasNode can be used to determine if a keying relationship exists with a
	// node.
	HasNode(nid *id.ID) bool

	// NumRegisteredNodes returns the total number of nodes we have a keying
	// relationship with.
	NumRegisteredNodes() int

	// TriggerNodeRegistration triggers the negotiation of a keying relationship
	// with a given node.
	TriggerNodeRegistration(nid *id.ID)

	// GetRoundResults adjudicates on the rounds requested. Checks if they are
	// older rounds or in progress rounds.
	GetRoundResults(timeout time.Duration, roundCallback RoundEventCallback,
		roundList ...id.Round)

	// LookupHistoricalRound looks up the passed historical round on the network.
	// GetRoundResults does this lookup when needed, generally that is
	// preferable
	LookupHistoricalRound(
		rid id.Round, callback rounds.RoundResultCallback) error

	// SendToAny can be used to send the comm to any gateway in the network.
	SendToAny(sendFunc func(host *connect.Host) (interface{}, error),
		stop *stoppable.Single) (interface{}, error)

	// SendToPreferred sends to a specific gateway, doing so through another
	// gateway as a proxy if not directly connected.
	SendToPreferred(targets []*id.ID, sendFunc gateway.SendToPreferredFunc,
		stop *stoppable.Single, timeout time.Duration) (interface{}, error)

	// GetHostParams returns the host params used when connecting to gateways.
	GetHostParams() connect.HostParams

	// GetAddressSpace returns the current address size of IDs. Blocks until an
	// address size is known.
	GetAddressSpace() uint8

	// RegisterAddressSpaceNotification returns a channel that will trigger for
	// every address space size update. The provided tag is the unique ID for
	// the channel. Returns an error if the tag is already used.
	RegisterAddressSpaceNotification(tag string) (chan uint8, error)

	// UnregisterAddressSpaceNotification stops broadcasting address space size
	// updates on the channel with the specified tag.
	UnregisterAddressSpaceNotification(tag string)

	// GetInstance returns the network instance object, which tracks the
	// state of the network.
	GetInstance() *network.Instance

	// GetVerboseRounds returns stringification of verbose round info.
	GetVerboseRounds() string
}

func NewClient

func NewClient(params Params, comms *commClient.Comms, session storage.Session,
	rng *fastRNG.StreamGenerator, events event.Reporter) (Client, error)

NewClient builds a new reception client object using inputted key fields.

type ClientErrorReport

type ClientErrorReport func(source, message, trace string)

type CmixMessageBuffer

type CmixMessageBuffer struct {
	// contains filtered or unexported fields
}

CmixMessageBuffer wraps the message buffer to store and load raw cMix messages.

func LoadCmixMessageBuffer

func LoadCmixMessageBuffer(kv versioned.KV, key string) (*CmixMessageBuffer, error)

func NewOrLoadCmixMessageBuffer

func NewOrLoadCmixMessageBuffer(kv versioned.KV, key string) (
	*CmixMessageBuffer, error)

func (*CmixMessageBuffer) Add

func (cmb *CmixMessageBuffer) Add(msg format.Message, recipient *id.ID,
	params CMIXParams)

func (*CmixMessageBuffer) AddProcessing

func (cmb *CmixMessageBuffer) AddProcessing(msg format.Message, recipient *id.ID,
	params CMIXParams)

func (*CmixMessageBuffer) Failed

func (cmb *CmixMessageBuffer) Failed(msg format.Message, recipient *id.ID)

func (*CmixMessageBuffer) Next

func (cmb *CmixMessageBuffer) Next() (format.Message, *id.ID, CMIXParams, bool)

func (*CmixMessageBuffer) Succeeded

func (cmb *CmixMessageBuffer) Succeeded(msg format.Message, recipient *id.ID)

type ManyMessageAssembler added in v4.4.4

type ManyMessageAssembler func(rid id.Round) ([]TargetedCmixMessage, error)

ManyMessageAssembler func accepts a round ID, returning a TargetedCmixMessage. This allows users to pass in a payload which will contain the round ID over which the message is sent.

type MessageAssembler

type MessageAssembler func(rid id.Round) (fingerprint format.Fingerprint,
	service Service, payload, mac []byte, err error)

MessageAssembler func accepts a round ID, returning fingerprint, service, payload & mac. This allows users to pass in a payload which will contain the round ID over which the message is sent.

type NodeMap

type NodeMap map[id.ID]bool

NodeMap represents a map of nodes and whether they have been blacklisted. This is designed for use with CMIXParams.BlacklistedNodes

func (NodeMap) MarshalJSON

func (nm NodeMap) MarshalJSON() ([]byte, error)

MarshalJSON adheres to the json.Marshaler interface.

func (*NodeMap) UnmarshalJSON

func (nm *NodeMap) UnmarshalJSON(data []byte) error

UnmarshalJSON adheres to the json.Unmarshaler interface.

type Params

type Params struct {
	// TrackNetworkPeriod determines how frequently follower threads are started.
	TrackNetworkPeriod time.Duration

	// MaxCheckedRounds is the maximum number of rounds to check in a single
	// iterations network updates.
	MaxCheckedRounds uint

	// RegNodesBufferLen is the size of the buffer of nodes to register.
	RegNodesBufferLen uint

	// NetworkHealthTimeout is the longest delay between network events for
	// health tracker to denote that the network is in a bad state.
	NetworkHealthTimeout time.Duration

	// ParallelNodeRegistrations is the number of parallel node registrations
	// that the client is capable of.
	ParallelNodeRegistrations uint

	// KnownRoundsThreshold dictates how far back in rounds the network should
	// actually check.
	KnownRoundsThreshold uint

	// FastPolling determines verbosity of network updates while polling. If
	// true, client receives a filtered set of updates. If false, client
	// receives the full list of network updates.
	FastPolling bool

	// VerboseRoundTracking determines if the state of every round processed is
	// tracked in memory. This is very memory intensive and is primarily used
	// for debugging.
	VerboseRoundTracking bool

	// ReplayRequests Resends auth requests up the stack if received multiple
	// times.
	ReplayRequests bool

	// MaxParallelIdentityTracks is the maximum number of parallel identities
	// the system will poll in one iteration of the follower
	MaxParallelIdentityTracks uint

	// ClockSkewClamp is the window (+/-) in which clock skew is
	// ignored and local time is used
	ClockSkewClamp time.Duration

	// EnableImmediateSending tells the registrar to allow use of ephemeral
	// ED keys to send to nodes before registration has completed.
	EnableImmediateSending bool

	// DisableNodeRegistration tells the registrar to disable the registration
	// subsystem. THIS SHOULD ONLY BE USED IN TESTING.
	DisableNodeRegistration bool

	// WhitelistedGateways is a list of gateway IDs which, if set, will be used
	// to create a GatewayFilter for the hostpool, ensuring we only connect to
	// gateways in this list.
	WhitelistedGateways []string

	Rounds     rounds.Params
	Pickup     pickup.Params
	Message    message.Params
	Historical rounds.Params
}

func GetDefaultParams

func GetDefaultParams() Params

GetDefaultParams returns a Params object containing the default parameters.

func GetParameters

func GetParameters(params string) (Params, error)

GetParameters returns the default Params, or override with given parameters, if set.

func (Params) MarshalJSON

func (p Params) MarshalJSON() ([]byte, error)

MarshalJSON adheres to the json.Marshaler interface.

func (*Params) UnmarshalJSON

func (p *Params) UnmarshalJSON(data []byte) error

UnmarshalJSON adheres to the json.Unmarshaler interface.

type RemoteFilter

type RemoteFilter struct {
	// contains filtered or unexported fields
}

func NewRemoteFilter

func NewRemoteFilter(data *mixmessages.ClientBloom) *RemoteFilter

func (*RemoteFilter) FirstRound

func (rf *RemoteFilter) FirstRound() id.Round

func (*RemoteFilter) GetFilter

func (rf *RemoteFilter) GetFilter() *bloom.Bloom

func (*RemoteFilter) LastRound

func (rf *RemoteFilter) LastRound() id.Round

type RoundEventCallback

type RoundEventCallback func(allRoundsSucceeded, timedOut bool, rounds map[id.Round]RoundResult)

RoundEventCallback interface which reports the requested rounds. Designed such that the caller may decide how much detail they need. allRoundsSucceeded:

Returns false if any rounds in the round map were unsuccessful.
Returns true if ALL rounds were successful

timedOut:

   Returns true if any of the rounds timed out while being monitored
	  Returns false if all rounds statuses were returned

rounds contains a mapping of all previously requested rounds to

their respective round results

type RoundLookupStatus

type RoundLookupStatus uint

RoundLookupStatus is the enum of possible round results to pass back

const (
	TimeOut RoundLookupStatus = iota
	Failed
	Succeeded
)

func (RoundLookupStatus) String

func (rr RoundLookupStatus) String() string

type RoundResult

type RoundResult struct {
	Status RoundLookupStatus
	Round  rounds.Round
}

type RoundState

type RoundState uint8
const (
	Unchecked RoundState = iota
	Unknown
	NoMessageAvailable
	MessageAvailable
	Abandoned
)

func (RoundState) String

func (rs RoundState) String() string

type RoundTracker

type RoundTracker struct {
	// contains filtered or unexported fields
}

func NewRoundTracker

func NewRoundTracker() *RoundTracker

func (*RoundTracker) String

func (rt *RoundTracker) String() string

type SendCmixCommsInterface

type SendCmixCommsInterface interface {
	// SendPutMessage places a cMix message on the gateway to be sent through
	// cMix.
	SendPutMessage(host *connect.Host, message *pb.GatewaySlot,
		timeout time.Duration) (*pb.GatewaySlotResponse, error)

	// SendPutManyMessages places a list of cMix messages on the gateway to be
	// sent through cMix.
	SendPutManyMessages(host *connect.Host, messages *pb.GatewaySlots,
		timeout time.Duration) (*pb.GatewaySlotResponse, error)
}

SendCmixCommsInterface is the interface for Send comms; allows mocking this in testing.

type Service added in v4.7.1

type Service interface {
	Hash(pickup *id.ID, contents []byte) ([]byte, error)
}

A Service is an operator which creates a tag on the message which can be used, without leaking metadata, to find if a message is for a specific party. The tag fits in the 200 bit "SIH" (Service Identification Hash) field on the cmix message. They come in two flavors, message.Service, Which has a single tag which is matched on, and message.CompressedService which used and encrypted bloom filter to compress multiple SIH tags into the field. It takes in the ID that is being sent to as well as the contents of the message.

type TargetedCmixMessage

type TargetedCmixMessage struct {
	Recipient   *id.ID
	Payload     []byte
	Fingerprint format.Fingerprint
	Service     Service
	Mac         []byte
}

TargetedCmixMessage defines a recipient target pair in a sendMany cMix message.

Directories

Path Synopsis
package clockSkew tracks local clock skew relative to gateways.
package clockSkew tracks local clock skew relative to gateways.
This file is compiled for all architectures except WebAssembly.
This file is compiled for all architectures except WebAssembly.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL