proto

package
v0.6.1 Latest Latest
Warning

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

Go to latest
Published: Jan 1, 2024 License: BSD-3-Clause Imports: 13 Imported by: 1

Documentation

Overview

Package proto defines the abstraction for Fit Protocol.

Fit Protocol is the core of a Fit file and it's the fundamental building block for decoding and encoding fit files.

Index

Constants

View Source
const (
	MesgDefinitionMask         = 0b01000000 // Mask for determining if the message type is a message definition.
	MesgNormalHeaderMask       = 0b00000000 // Mask for determining if the message type is a normal message data .
	MesgCompressedHeaderMask   = 0b10000000 // Mask for determining if the message type is a compressed timestamp message data.
	LocalMesgNumMask           = 0b00001111 // Mask for mapping normal message data to the message definition.
	CompressedLocalMesgNumMask = 0b01100000 // Mask for mapping compressed timestamp message data to the message definition. Used with CompressedBitShift.
	CompressedTimeMask         = 0b00011111 // Mask for measuring time offset value from header. Compressed timestamp is using 5 least significant bits (lsb) of header
	DevDataMask                = 0b00100000 // Mask for determining if a message contains developer fields.

	CompressedBitShift = 5 // Used for right shifting the 5 least significant bits (lsb) of compressed ti

	DefaultFileHeaderSize byte   = 14     // The preferred size is 14
	DataTypeFIT           string = ".FIT" // FIT is a constant string ".FIT"

	FieldNumTimestamp = 253 // Field Num for timestamp across all defined messages in the profile.
)
View Source
const (
	MajorVersionShift = 4
	MajorVersionMask  = 0x0F << MajorVersionShift
	MinorVersionMask  = 0x0F

	V1   Version = 1 << MajorVersionShift // V1 is Version 1.0
	V2   Version = 2 << MajorVersionShift // V2 is Version 2.0
	Vmax         = V2                     // Vmax is an alias for the current latest version.
)
View Source
const MaxBytesPerMessage = 1 + (255 * 255) + (255 * 255) + 1

m.Header + ((max cap of m.Fields) * (n value)) + ((max cap of m.DeveloperFields) * (n value)) + cap

Variables

View Source
var ErrProtocolVersionNotSupported = errors.New("protocol version not supported")
View Source
var ErrProtocolViolation = errors.New("protocol violation")

Functions

func LocalMesgNum

func LocalMesgNum(header byte) byte

LocalMesgNum extracts LocalMesgNum from message header.

func Validate

func Validate(version byte) error

Validate checks whether given version is a valid version.

func VersionMajor

func VersionMajor(version byte) byte

VersionMajor returns major value of given version

func VersionMinor

func VersionMinor(version byte) byte

VersionMinor returns minor value of given version

Types

type Component

type Component struct {
	FieldNum   byte
	Scale      float64
	Offset     float64
	Accumulate bool
	Bits       byte // bit value max 32
}

Component is a way of compressing one or more fields into a bit field expressed in a single containing field. The component can be expanded as a main Field in a Message or to update the value of the destination main Field.

type DeveloperField

type DeveloperField struct {
	Num                byte
	DeveloperDataIndex byte
	Size               byte
	NativeMesgNum      typedef.MesgNum
	NativeFieldNum     byte
	Name               string
	Type               basetype.BaseType
	Units              string
	Value              any
}

Developer Field is a way to add custom data fields to existing messages. Developer Data Fields can be added to any message at runtime by providing a self-describing field definition. Developer Data Fields are also used by the Connect IQ FIT Contributor library, allowing Connect IQ apps and data fields to include custom data in FIT Activity files during the recording of activities. [Added since protocol version 2.0]

NOTE: If Developer Field contains a valid NativeMesgNum and NativeFieldNum, the value should be treated as native value (scale, offset, etc shall apply).

func (DeveloperField) Clone

func (f DeveloperField) Clone() DeveloperField

Clone clones DeveloperField

type DeveloperFieldDefinition

type DeveloperFieldDefinition struct {
	Num                byte // Map to the `field_definition_number` of a `field_description` Message.
	Size               byte // Size (in bytes) of the specified FIT message’s field
	DeveloperDataIndex byte // Maps to the `developer_data_index“ of a `developer_data_id` Message
}

FieldDefinition is the definition of the upcoming developer field within the message's structure.

type Field

type Field struct {
	// PERF: Embedding the struct as a pointer to avoid runtime duffcopy when creating a field since FieldBase should not be altered.
	*FieldBase

	// The decoded value, composed by decoder, will always in a form of a primitive-type (or a slice of primitive types):
	// - int8, uint8, int16, uint16, int32, uint32, int64, uint64, float32, float64 and string.
	// - []int8, []uint8, []int16, []uint16, []int32, []uint32, []int64, []uint64, []float32, []float64 and []string.
	//
	// When the field is manually composed, you may use type-defined value as long as it refer to any of primitive-types
	// (e.g. typedef.FileActivity). However, please note that marshaling type-defined value requires reflection.
	//
	// NOTE: You can not use distinct types such as int and uint.
	Value any

	// A flag to detect whether this field is generated through component expansion.
	IsExpandedField bool
}

Field represents the full representation of a field, as specified in the Global Fit Profile.

func (Field) Clone

func (f Field) Clone() Field

Clone clones Field

func (*Field) SubFieldSubtitution

func (f *Field) SubFieldSubtitution(mesgRef *Message) *SubField

SubFieldSubstitution returns any sub-field that can substitute the properties interpretation of the parent Field (Dynamic Field).

func (Field) WithValue

func (f Field) WithValue(v any) Field

WithValue returns a Field containing v value.

type FieldBase

type FieldBase struct {
	Name       string              // Defined in the Global FIT profile for the specified FIT message, otherwise its a manufaturer specific name (defined by manufacturer).
	Num        byte                // Defined in the Global FIT profile for the specified FIT message, otherwise its a manufaturer specific number (defined by manufacturer). (255 == invalid)
	Type       profile.ProfileType // Type is defined type that serves as an abstraction layer above base types (primitive-types), e.g. DateTime is a time representation in uint32.
	Array      bool                // Flag whether the value of this field is an array
	Scale      float64             // A scale or offset specified in the FIT profile for binary fields (sint/uint etc.) only. the binary quantity is divided by the scale factor and then the offset is subtracted. (default: 1)
	Offset     float64             // A scale or offset specified in the FIT profile for binary fields (sint/uint etc.) only. the binary quantity is divided by the scale factor and then the offset is subtracted. (default: 0)
	Units      string              // Units of the value, such as m (meter), m/s (meter per second), s (second), etc.
	Accumulate bool                // Flag to indicate if the value of the field is accumulable.
	Components []Component         // List of components
	SubFields  []SubField          // List of sub-fields
}

FieldBase acts as a fundamental representation of a field as defined in the Global Fit Profile. The value of this representation should not be altered, except in the case of an unknown field.

type FieldDefinition

type FieldDefinition struct {
	Num      byte              // The field definition number
	Size     byte              // The size of the upcoming value
	BaseType basetype.BaseType // The type of the upcoming value to be represented
}

FieldDefinition is the definition of the upcoming field within the message's structure.

type FileHeader

type FileHeader struct {
	Size            byte   // Header size either 12 (legacy) or 14.
	ProtocolVersion byte   // The Fit Protocol version which is being used to encode the Fit file.
	ProfileVersion  uint16 // The Fit Profile Version (associated with data defined in Global Fit Profile).
	DataSize        uint32 // The size of the messages in bytes (this field will be automatically updated by the encoder)
	DataType        string // ".FIT" (a string constant)
	CRC             uint16 // Cyclic Redundancy Check 16-bit value to ensure the integrity if the header. (this field will be automatically updated by the encoder)
}

FileHeader is a Fit's FileHeader with either 12 bytes size without CRC or a 14 bytes size with CRC, while 14 bytes size is the preferred size.

func (*FileHeader) MarshalBinary

func (h *FileHeader) MarshalBinary() ([]byte, error)

type Fit

type Fit struct {
	FileHeader FileHeader // File Header contains either 12 or 14 bytes
	Messages   []Message  // Messages.
	CRC        uint16     // Cyclic Redundancy Check 16-bit value to ensure the integrity of the messages.
}

Fit represents a structure for Fit Files.

func (*Fit) WithMessages

func (f *Fit) WithMessages(messages ...Message) *Fit

WithMessages set Messages and return the pointer to the Fit.

type Message

type Message struct {
	Header          byte             // Message Header serves to distinguish whether the message is a Normal Data or a Compressed Timestamp Data. Unlike MessageDefinition, Message's Header should not contain Developer Data Flag.
	Num             typedef.MesgNum  // Global Message Number defined in Global Fit Profile, except number within range 0xFF00 - 0xFFFE are manufacturer specific number.
	Reserved        byte             // Currently undetermined; the default value is 0.
	Architecture    byte             // Architecture type / Endianness. Must be the same
	Fields          []Field          // List of Field
	DeveloperFields []DeveloperField // List of DeveloperField
}

Message is a FIT protocol message containing the data defined in the Message Definition

func (Message) Clone

func (m Message) Clone() Message

Clone clones Message.

func (*Message) FieldByNum

func (m *Message) FieldByNum(num byte) *Field

FieldByNum returns a pointer to the Field in a Message, if not found return nil.

func (*Message) FieldValueByNum added in v0.1.0

func (m *Message) FieldValueByNum(num byte) any

FieldValueByNum returns the value of the Field in a Messsage, if not found return nil.

func (*Message) MarshalBinary

func (m *Message) MarshalBinary() ([]byte, error)

func (*Message) RemoveFieldByNum

func (m *Message) RemoveFieldByNum(num byte)

RemoveFieldByNum removes Field in a Message by num.

func (Message) WithDeveloperFields

func (m Message) WithDeveloperFields(developerFields ...DeveloperField) Message

WithFields copies the provided fields into the message's fields.

func (Message) WithFieldValues

func (m Message) WithFieldValues(fieldNumValues map[byte]any) Message

WithFieldValues assigns the values of the targeted fields with the given map, where map[byte]any represents the field numbers and their respective values.

func (Message) WithFields

func (m Message) WithFields(fields ...Field) Message

WithFields copies the provided fields into the message's fields.

func (*Message) WriteTo added in v0.5.0

func (m *Message) WriteTo(w io.Writer) (n int64, err error)

WriteTo zero alloc marshal then copy it to w.

type MessageDefinition

type MessageDefinition struct {
	Header                    byte                       // The message definition header with mask 0b01000000.
	Reserved                  byte                       // Currently undetermined; the default value is 0.
	Architecture              byte                       // The Byte Order to be used to decode the values of both this message definition and the upcoming message. (0: Little-Endian, 1: Big-Endian)
	MesgNum                   typedef.MesgNum            // Global Message Number defined by factory (retrieved from Profile.xslx). (endianness of this 2 Byte value is defined in the Architecture byte)
	FieldDefinitions          []FieldDefinition          // List of the field definition
	DeveloperFieldDefinitions []DeveloperFieldDefinition // List of the developer field definition (only if Developer Data Flag is set in Header)
}

MessageDefinition is the definition of the upcoming data messages.

func CreateMessageDefinition

func CreateMessageDefinition(mesg *Message) (mesgDef MessageDefinition)

CreateMessageDefinition creates new MessageDefinition base on given Message.

func (MessageDefinition) Clone

Clone clones MessageDefinition

func (*MessageDefinition) MarshalBinary

func (m *MessageDefinition) MarshalBinary() ([]byte, error)

func (*MessageDefinition) WriteTo added in v0.5.0

func (m *MessageDefinition) WriteTo(w io.Writer) (n int64, err error)

WriteTo zero alloc marshal then copy it to w.

type SubField

type SubField struct {
	Name       string
	Type       profile.ProfileType
	Scale      float64
	Offset     float64
	Units      string
	Maps       []SubFieldMap
	Components []Component
}

SubField is a dynamic interpretation of the main Field in a Message when the SubFieldMap mapping match. See SubFieldMap's docs.

func (SubField) Clone

func (s SubField) Clone() SubField

Clone clones SubField

type SubFieldMap

type SubFieldMap struct {
	RefFieldNum   byte
	RefFieldValue int64
}

SubFieldMap is the mapping between SubField and and the corresponding main Field in a Message. When any Field in a Message has Field.Num == RefFieldNum and Field.Value == RefFieldValue, then the SubField containing this mapping can be interpreted as the main Field's properties (name, scale, type etc.)

type Validator

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

Validator is protocol validator

func NewValidator

func NewValidator(version Version) *Validator

NewValidator creates protocol validator base on given version.

func (*Validator) ValidateMessageDefinition

func (p *Validator) ValidateMessageDefinition(mesgDef *MessageDefinition) error

ValidateMessageDefinition validates whether the message definition contains unsupported data for the targeted version.

type Version

type Version byte

Version is Fit Protocol Version

func CreateVersion

func CreateVersion(major, minor byte) (Version, bool)

CreateVersion creates version from major and minor value, it can only create version up < Vmax.

Jump to

Keyboard shortcuts

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