Documentation ¶
Index ¶
- Constants
- Variables
- func BroadcastBrowseRequest(conn net.PacketConn) error
- func Browse(ctx context.Context, interfaceName string) (<-chan Result[*BrowseResponse], error)
- func ListenToBrowseResponses(ctx context.Context, interfaceName string) ([]net.PacketConn, <-chan Result[*BrowseResponse], error)
- func Mux(ctx context.Context, listener net.Listener, source SyncClient, ...) error
- func SendBrowseRequest(conn net.PacketConn, address string) error
- func Serve(ctx context.Context, listener net.Listener, source SyncClient, ...) error
- type BrowseRequest
- type BrowseResponse
- type Client
- type Conn
- type ConnOption
- func WithBusyTimeout(timeout int) ConnOption
- func WithConcurrentTransactionLimit(ct uint) ConnOption
- func WithDial(dial func(string, string) (io.ReadWriteCloser, error)) ConnOption
- func WithDialBackoff(backoffFactory func() backoff.BackOff) ConnOption
- func WithLeaseTimeout(timeout int) ConnOption
- func WithMeasureNetworkLatencyICMP() ConnOption
- func WithSendKeepAlive() ConnOption
- func WithWriter(writerFactory func(io.Writer) io.Writer) ConnOption
- type ConnProperties
- type ConnectRequest
- type ConnectResponse
- type Exception
- type Header
- type Idn
- type MessageType
- type PDU
- type PingRequest
- type PingResponse
- type ReadDataStateRequest
- type ReadDataStateResponse
- type ReadDescriptionRequest
- type ReadDescriptionResponse
- type ReadEverythingRequest
- type ReadEverythingResponse
- type ReadOnlyDataRequest
- type ReadOnlyDataResponse
- type Request
- type RequestOption
- type Result
- type SyncClient
- type WriteDataRequest
- type WriteDataResponse
Constants ¶
const ( ElmDataState uint16 = 0x0001 ElmName uint16 = 0x0002 ElmAttribute uint16 = 0x0004 ElmUnit uint16 = 0x0008 ElmMin uint16 = 0x0010 ElmMax uint16 = 0x0020 ElmData uint16 = 0x0040 )
Constants for the validElements field in ReadDescriptionResponse and ReadEverythingResponse
const BroadcastNameplateMsgType = MessageType(99)
const BrowseOnSlaveInterfaceRequestMsgType = MessageType(107)
const BrowseOnSlaveInterfaceResponseMsgType = MessageType(108)
const BrowseRequestMsgType = MessageType(91)
const BrowseResponseMsgType = MessageType(100)
const BusyResponseMsgType = MessageType(68)
const ConnectRequestMsgType = MessageType(63)
const ConnectResponseMsgType = MessageType(64)
const ConnectionError = uint16(1)
the server is not able to serve a TCP based S/IP connection. See TCP based communication initialization for further details.
const EchoMsgType = MessageType(32768)
const ExceptionMsgType = MessageType(67)
const IdentifyRequestMsgType = MessageType(93)
const IdentifyResponseMsgType = MessageType(94)
const InterfacesRequestMsgType = MessageType(103)
const InterfacesResponseMsgType = MessageType(104)
const NameplateRequestMsgType = MessageType(89)
const NameplateResponseMsgType = MessageType(90)
const PduProtocolMismatchError = uint16(6)
malformed PDU e.g. received UDP datagram does not correspond to the expected PDU size
const PduToLargeError = uint16(5)
request or response does not fit to the UDP datagram (limitation of PDU size)
const PingRequestMsgType = MessageType(65)
const PingResponseMsgType = MessageType(66)
const Port = 35021
Port is the default SIP port
const ReadApplicationsRequestMsgType = MessageType(137)
const ReadApplicationsResponseMsgType = MessageType(138)
const ReadDataStateRequestMsgType = MessageType(87)
const ReadDataStateResponseMsgType = MessageType(88)
const ReadDescriptionRequestMsgType = MessageType(73)
const ReadDescriptionResponseMsgType = MessageType(74)
const ReadEverythingRequestMsgType = MessageType(69)
const ReadEverythingResponseMsgType = MessageType(70)
const ReadNodesRequestMsgType = MessageType(139)
const ReadNodesResponseMsgType = MessageType(140)
const ReadOnlyDataRequestMsgType = MessageType(71)
const ReadOnlyDataResponseMsgType = MessageType(72)
const ReadSegmentRequestMsgType = MessageType(109)
const ReadSegmentResponseMsgType = MessageType(110)
const ReadSymbolDataRequestMsgType = MessageType(133)
const ReadSymbolDataResponseMsgType = MessageType(134)
const ReadSymbolDescriptionRequestMsgType = MessageType(131)
const ReadSymbolDescriptionResponseMsgType = MessageType(132)
const ReadSymbolEverythingRequestMsgType = MessageType(135)
const ReadSymbolEverythingResponseMsgType = MessageType(136)
const RemoteServiceRequestMsgType = MessageType(113)
const RemoteServiceResponseMsgType = MessageType(114)
const ReservedMsgType = MessageType(92)
const ResetRequestMsgType = MessageType(97)
const ResetResponseMsgType = MessageType(98)
const ServiceSpecificError = uint16(4)
Services are able to have their own error code. Further information are available in the SpecificErrorCode of the Exception structure. See also specific error code descriptions of the service invoked.
const SetIPRequestMsgType = MessageType(95)
const SetIPResponseMsgType = MessageType(96)
const SlavesRequestMsgType = MessageType(105)
const SlavesResponseMsgType = MessageType(106)
const SupportedUDPServicesMsgType = MessageType(61)
const SupportedUDPServicesResponseMsgType = MessageType(62)
const TimeoutError = uint16(2)
a timeout exceeds (see Timeouts for further details) or a TCP connection gets lost. Network activities are controlled by local timeout handling. If the server doesn't respond in time, this error code is used to indicate the error to the user on client-side.
const UnknownMessageTypeError = uint16(3)
s the server receives an unknown message type, it shall send an exception with this error code to the client. In case of a TCP based S/IP request the server returns the exception to the client and shall close the TCP stream socket connection.
const WatchdogRequestMsgType = MessageType(101)
const WatchdogResponseMsgType = MessageType(102)
const WriteAttributeRequestMsgType = MessageType(77)
const WriteAttributeResponseMsgType = MessageType(78)
const WriteDataBitsResponseMsgType = MessageType(86)
const WriteDataRequestBitsMsgType = MessageType(85)
const WriteDataRequestMsgType = MessageType(83)
const WriteDataResponseMsgType = MessageType(84)
const WriteMinMaxRequestMsgType = MessageType(81)
const WriteMinMaxResponseMsgType = MessageType(82)
const WriteNameRequestMsgType = MessageType(75)
const WriteNameResponseMsgType = MessageType(76)
const WriteSymbolDataResponseMsgType = MessageType(142)
const WriteSymbolRequestDataMsgType = MessageType(141)
const WriteUnitRequestMsgType = MessageType(79)
const WriteUnitResponseMsgType = MessageType(80)
Variables ¶
var Error = errors.New("S/IP")
Error defines the S/IP error class. Base of all other S/IP errors
var ErrorClosed = fmt.Errorf("%w: Connection closed", Error)
var ErrorInvalidRequestMessageType = fmt.Errorf("%w: Invalid request message type", Error)
var ErrorInvalidResponseMessageType = fmt.Errorf("%w: Invalid response message type", Error)
var ErrorRetriesExceeded = fmt.Errorf("%w: Reconnect timeout exceeded", Error)
var ErrorTimeout = fmt.Errorf("%w: Timeout", Error)
Functions ¶
func BroadcastBrowseRequest ¶
func BroadcastBrowseRequest(conn net.PacketConn) error
BroadcastBrowseRequest broadcasts a BrowseRequest on the passed net.PacketConn from ListenToBrowseResponses. Note that the net.PacketConn will be closed when ListenToBrowseResponses is canceled.
func Browse ¶
Browse listens to BrowseResponses and broadcasts one BrowseRequest on the given interface. The Listening ends when ctx is canceled.
func ListenToBrowseResponses ¶
func ListenToBrowseResponses(ctx context.Context, interfaceName string) ([]net.PacketConn, <-chan Result[*BrowseResponse], error)
ListenToBrowseResponses listens on interfaceName for BrowseResponses until ctx is canceled. It automatically reserves a free port for listening. The returned net.PacketConn should be used to send BrowseRequests on the listened port. The channel returns any valid BrowseResponse that is received, all errors occured while parsing received packages and all errors with the net.PacketConn. The connection and the channel are closed in case of errors of the latter category.
func Mux ¶
func Mux(ctx context.Context, listener net.Listener, source SyncClient, options ...ConnOption) error
Mux creates a multiplexer which listens on the given listener and forwards the S/IP requests to the source. Reads are optimized by reading only once and broadcasting the response to all listeners. Mux is useful when the source has limited resources and can't handle a larger number of multiple connections.
func SendBrowseRequest ¶
func SendBrowseRequest(conn net.PacketConn, address string) error
SendBrowseRequest sends a BrowseRequest on the passed net.PacketConn to a dedicated IP address.
func Serve ¶
func Serve(ctx context.Context, listener net.Listener, source SyncClient, options ...ConnOption) error
Serve creates a server which listens on the given listener and forwards the S/IP requests to the source.
Types ¶
type BrowseRequest ¶
type BrowseRequest struct { IPAddress [4]byte MasterOnly bool LowerSercosAddress uint16 UpperSercosAddress uint16 }
func (*BrowseRequest) MessageType ¶
func (b *BrowseRequest) MessageType() MessageType
type BrowseResponse ¶
type BrowseResponse struct { DisplayName []byte HostNameLength uint32 HostName []byte // contains filtered or unexported fields }
func (*BrowseResponse) MessageType ¶
func (b *BrowseResponse) MessageType() MessageType
type Client ¶
type Client interface { ConnProperties SyncClient GoPing(options ...RequestOption) <-chan error GoReadEverything(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) <-chan Result[ReadEverythingResponse] GoReadOnlyData(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) <-chan Result[ReadOnlyDataResponse] GoReadDescription(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) <-chan Result[ReadDescriptionResponse] GoReadDataState(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) <-chan Result[ReadDataStateResponse] GoWriteData(slaveIndex, slaveExtension int, idn uint32, data []byte, options ...RequestOption) <-chan error Close() error Closed() bool }
Client is like Conn, but with automatic reconnect, a configurable timeout strategy for reconnection, the possibility to cancel single requests with a context.Context and to automatically retry requests.
Ping, ReadXXX, WriteData work like the Conn methods but try to reconnect when the underlying connection has been closed meanwhile. Their further behavior can be configured with options. The GoXXX variants of the methods work asynchronously by returning a channel.
Close closes the currently open connection, if there is anyone yet.
func NewClient ¶
func NewClient(network, address string, options ...ConnOption) Client
NewClient creates a new Client. The backoff strategy for failed connects can be configured with the WithDialBackoff option. If the option is not given, the backoff strategy is an exponential backoff, starting with a backoff time of 500ms, exponentially incremented by factor 1.5, with an overall timeout of 10 seconds. All other options are ignored.
type Conn ¶
type Conn interface { ConnProperties Ping(ctx context.Context) error ReadEverything(ctx context.Context, slaveIndex, slaveExtension int, idn uint32) (ReadEverythingResponse, error) ReadOnlyData(ctx context.Context, slaveIndex, slaveExtension int, idn uint32) (ReadOnlyDataResponse, error) ReadDescription(ctx context.Context, slaveIndex, slaveExtension int, idn uint32) (ReadDescriptionResponse, error) ReadDataState(ctx context.Context, slaveIndex, slaveExtension int, idn uint32) (ReadDataStateResponse, error) WriteData(ctx context.Context, slaveIndex, slaveExtension int, idn uint32, data []byte) error Close() error Closed() bool }
Conn is a SIP client connection. It can be used to read and write SERCOS parameter values. Its lifetime starts with Dial and ends when the user calls Close, the server does not answer in timely manner (BusyTimeout) or the underlying net.Conn has been closed.
When Dial is successful, the S/IP Connect procedure has already been executed. Ping, ReadXXX, WriteData send the according Request and try to receive the matching Response. They return either with an error or when the Response has been received successfuly.
Conn is able to execute more than one concurrent transaction, see WithConcurrentTransactionLimit.
type ConnOption ¶
type ConnOption func(c *connOptions) error
ConnOption is option for Conn
func WithBusyTimeout ¶
func WithBusyTimeout(timeout int) ConnOption
WithBusyTimeout sets the BusyTimeout to negotiate with the server in ms. Default is 2000ms.
func WithConcurrentTransactionLimit ¶
func WithConcurrentTransactionLimit(ct uint) ConnOption
WithConcurrentTransactionLimit limits the number of concurrent requests sent. If the option is not given in Dial, the concurrency is not limited.
func WithDial ¶
func WithDial(dial func(string, string) (io.ReadWriteCloser, error)) ConnOption
WithDial surpasses the net.Conn from the Dial function. This option can be used for testing, logging, middleware purposes in general, or exotic connection types.
func WithDialBackoff ¶
func WithDialBackoff(backoffFactory func() backoff.BackOff) ConnOption
WithDialBackoff configures the backoff strategy for failed connects. See https://pkg.go.dev/github.com/cenkalti/backoff/v4 for more information about backoff strategies. Default is an exponential backoff, starting with a backoff time of 500ms, exponentially incremented by factor 1.5, with an overall timeout of 10 seconds.
func WithLeaseTimeout ¶
func WithLeaseTimeout(timeout int) ConnOption
WithLeaseTimeout sets the LeaseTimeout to negotiate with the server in ms. Default is 10000ms.
func WithMeasureNetworkLatencyICMP ¶
func WithMeasureNetworkLatencyICMP() ConnOption
WithMeasureNetworkLatencyICMP measures the network latency with an ICMP ping. If not set, the network latency is measured with S/IP Ping, which might lead to different latency results, depending on the server implementation. Note that ICMP ping requires specific system config options mentioned here: https://github.com/prometheus-community/#supported-operating-systems
func WithSendKeepAlive ¶
func WithSendKeepAlive() ConnOption
WithSendKeepAlive configures the connection that it is sending Ping requests shortly before the LeaseTimeout ends.
func WithWriter ¶
func WithWriter(writerFactory func(io.Writer) io.Writer) ConnOption
WithWriter allows to control the way requests are sent to the net.Conn. This can be useful to group request and/or send them at defined points in time.
type ConnProperties ¶
type ConnProperties interface { Connected() bool BusyTimeout() time.Duration LeaseTimeout() time.Duration LastReceived() time.Time MessageTypes() []uint32 }
ConnProperties describes the properties of a Conn.
Connected() bool
If the Conn is currently connected
BusyTimeout() time.Duration
Time span after the server acknowledged to send a Busy response if it is not able to respond to open requests.
LeaseTimeout() time.Duration
Time span without requests after the server will close the connection. When the WithKeepAlive() option is used, the connection will send a Ping request shortly before this time span ends.
LastReceived() time.Time
Timestamp when the last response from the server was received. The Client uses this information to decide if to send a request over the current connection or to open a new one. By this, timeouts caused by servers which do not close the net.Conn directly after they decide to close the SIP connection can be evaded.
type ConnectRequest ¶
type ConnectRequest struct { // S/IP protocol version // version=1 shall be used for this protocol version Version uint32 // requested busy-timeout the server should use, in milliseconds BusyTimeout uint32 // requested lease-timeout the server should use, in milliseconds LeaseTimeout uint32 }
ConnectRequest MessageType 63 In order to initiate a S/IP connection, the client sends a ConnectRequest PDU to the server. This request contains the desired S/IP version number and desired timeout values for the connection.
func (*ConnectRequest) MessageType ¶
func (c *ConnectRequest) MessageType() MessageType
type ConnectResponse ¶
type ConnectResponse struct { // supported Request MessageTypes of the server on this TCP connection. // The client must only use these message types in a request. MessageTypes []uint32 // contains filtered or unexported fields }
func (*ConnectResponse) MessageType ¶
func (c *ConnectResponse) MessageType() MessageType
type Exception ¶
Exception, MessageType: 67. It contains a common error code and an optional service specific error code.
func (*Exception) MessageType ¶
func (c *Exception) MessageType() MessageType
type Header ¶
type Header struct { TransactionID uint32 MessageType MessageType }
type MessageType ¶
type MessageType uint32
type PingRequest ¶
type PingRequest struct{}
func (*PingRequest) MessageType ¶
func (c *PingRequest) MessageType() MessageType
type PingResponse ¶
type PingResponse struct{}
func (*PingResponse) MessageType ¶
func (c *PingResponse) MessageType() MessageType
type ReadDataStateRequest ¶
type ReadDataStateRequest Request
func (*ReadDataStateRequest) Init ¶
func (r *ReadDataStateRequest) Init(slaveIndex, slaveExtension int, idn uint32)
func (*ReadDataStateRequest) MessageType ¶
func (r *ReadDataStateRequest) MessageType() MessageType
type ReadDataStateResponse ¶
type ReadDataStateResponse struct {
DataState uint16
}
func (*ReadDataStateResponse) MessageType ¶
func (r *ReadDataStateResponse) MessageType() MessageType
type ReadDescriptionRequest ¶
type ReadDescriptionRequest Request
func (*ReadDescriptionRequest) Init ¶
func (r *ReadDescriptionRequest) Init(slaveIndex, slaveExtension int, idn uint32)
func (*ReadDescriptionRequest) MessageType ¶
func (r *ReadDescriptionRequest) MessageType() MessageType
type ReadDescriptionResponse ¶
type ReadDescriptionResponse struct { Name []byte Unit []byte // contains filtered or unexported fields }
func (*ReadDescriptionResponse) MessageType ¶
func (r *ReadDescriptionResponse) MessageType() MessageType
type ReadEverythingRequest ¶
type ReadEverythingRequest Request
func (*ReadEverythingRequest) MessageType ¶
func (r *ReadEverythingRequest) MessageType() MessageType
type ReadEverythingResponse ¶
type ReadEverythingResponse struct { Name []byte Unit []byte Data []byte // contains filtered or unexported fields }
func (*ReadEverythingResponse) MessageType ¶
func (r *ReadEverythingResponse) MessageType() MessageType
type ReadOnlyDataRequest ¶
type ReadOnlyDataRequest Request
func (*ReadOnlyDataRequest) Init ¶
func (r *ReadOnlyDataRequest) Init(slaveIndex, slaveExtension int, idn uint32)
func (*ReadOnlyDataRequest) MessageType ¶
func (r *ReadOnlyDataRequest) MessageType() MessageType
type ReadOnlyDataResponse ¶
type ReadOnlyDataResponse struct { Data []byte // contains filtered or unexported fields }
func (*ReadOnlyDataResponse) MessageType ¶
func (r *ReadOnlyDataResponse) MessageType() MessageType
type RequestOption ¶
type RequestOption func(r *requestOptions) error
RequestOption is a option for any kind of request
func WithContext ¶
func WithContext(ctx context.Context) RequestOption
WithContext allows to cancel a request with a context.
func WithRetries ¶
func WithRetries(retries uint) RequestOption
WithRetries configures how often a request is retried when it fails. Default is no retry.
func WithTimeout ¶
func WithTimeout(timeout time.Duration) RequestOption
WithTimeout allows to cancel a request with a timeout.
type SyncClient ¶
type SyncClient interface { Ping(options ...RequestOption) error ReadEverything(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) (ReadEverythingResponse, error) ReadOnlyData(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) (ReadOnlyDataResponse, error) ReadDescription(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) (ReadDescriptionResponse, error) ReadDataState(slaveIndex, slaveExtension int, idn uint32, options ...RequestOption) (ReadDataStateResponse, error) WriteData(slaveIndex, slaveExtension int, idn uint32, data []byte, options ...RequestOption) error }
type WriteDataRequest ¶
type WriteDataRequest struct { Data []byte // contains filtered or unexported fields }
func (*WriteDataRequest) MessageType ¶
func (w *WriteDataRequest) MessageType() MessageType
type WriteDataResponse ¶
type WriteDataResponse struct{}
func (*WriteDataResponse) MessageType ¶
func (c *WriteDataResponse) MessageType() MessageType
Source Files ¶
- browse.go
- client.go
- conn.go
- conn_connect_close.go
- conn_options.go
- conn_send_recv.go
- conn_type.go
- connect.go
- exception.go
- header.go
- idn.go
- message_types.go
- mux.go
- ping.go
- readdatastate.go
- readdescription.go
- readeverything.go
- readonlydata.go
- result.go
- server.go
- sip.go
- timeoutreader.go
- udp.go
- util.go
- write.go