Skip to content

Commit f58dd27

Browse files
committed
fix: Utilize hoplimit for multicast
If the hoplimit is set, it will be used. If not set, the default values defined in the [OCF Core Specification](https://openconnectivity.org/specs/OCF_Core_Specification.pdf) section 12.2.9 will be used. Default values: - For "224.0.1.187:5683", the hoplimit is set to 1. - For "[ff02::158]:5683", the hoplimit is set to 1. - For "[ff03::158]:5683", the hoplimit is set to 255. - For "[ff05::158]:5683", the hoplimit is set to 255.
1 parent 2f1f7eb commit f58dd27

File tree

2 files changed

+39
-6
lines changed

2 files changed

+39
-6
lines changed

client/core/client.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,7 +80,7 @@ func WithTLS(tlsConfig *TLSConfig) OptionFunc {
8080

8181
// DiscoveryConfiguration setup discovery configuration
8282
type DiscoveryConfiguration struct {
83-
MulticastHopLimit int // default: 2, min value: 1 - don't pass through router, max value: 255, https://tools.ietf.org/html/rfc2460#section-3
83+
MulticastHopLimit int // default: {224.0.1.187:5683, ff02::158]:5683} = 1, {[ff03::158]:5683, [ff05::158]:5683} = 255, https://openconnectivity.org/specs/OCF_Core_Specification.pdf 12.2.9
8484
MulticastAddressUDP4 []string // default: "[224.0.1.187:5683] (client.DiscoveryAddressUDP4), empty: don't use ipv4 multicast"
8585
MulticastAddressUDP6 []string // default: "[ff02::158]:5683", "[ff03::158]:5683", "[ff05::158]:5683]"] (client.DiscoveryAddressUDP6), empty: don't use ipv6 multicast"
8686
MulticastOptions []coapNet.MulticastOption
@@ -151,7 +151,7 @@ func (c *Client) getDeviceConfiguration() DeviceConfiguration {
151151

152152
func DefaultDiscoveryConfiguration() DiscoveryConfiguration {
153153
return DiscoveryConfiguration{
154-
MulticastHopLimit: 2,
154+
MulticastHopLimit: 0, // will be set to 1 or 255 based on address
155155
MulticastAddressUDP4: DiscoveryAddressUDP4,
156156
MulticastAddressUDP6: DiscoveryAddressUDP6,
157157
MulticastOptions: []coapNet.MulticastOption{coapNet.WithMulticastInterfaceError(func(iface *net.Interface, err error) {

client/core/discover.go

Lines changed: 37 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -36,9 +36,16 @@ import (
3636
// See the section 10.4 on the line 2482 of the Core specification:
3737
// https://openconnectivity.org/specs/OCF_Core_Specification_v2.0.0.pdf
3838
// https://iotivity.org/documentation/linux/programmers-guide
39+
const (
40+
DiscoveryAddressUDP4Local = "224.0.1.187:5683"
41+
DiscoveryAddressUDP6LinkLocal = "[ff02::158]:5683"
42+
DiscoveryAddressUDP6RealmLocal = "[ff03::158]:5683"
43+
DiscoveryAddressUDP6SiteLocal = "[ff05::158]:5683"
44+
)
45+
3946
var (
40-
DiscoveryAddressUDP4 = []string{"224.0.1.187:5683"}
41-
DiscoveryAddressUDP6 = []string{"[ff02::158]:5683", "[ff03::158]:5683", "[ff05::158]:5683"}
47+
DiscoveryAddressUDP4 = []string{DiscoveryAddressUDP4Local}
48+
DiscoveryAddressUDP6 = []string{DiscoveryAddressUDP6LinkLocal, DiscoveryAddressUDP6RealmLocal, DiscoveryAddressUDP6SiteLocal}
4249
)
4350

4451
type DiscoveryHandler = func(conn *client.Conn, req *pool.Message)
@@ -89,6 +96,24 @@ func (d *DiscoveryClient) Close() error {
8996
return err
9097
}
9198

99+
// See the section 12.2.9 https://openconnectivity.org/specs/OCF_Core_Specification.pdf
100+
var defaultHopLimit = map[string]int{
101+
DiscoveryAddressUDP4Local: 1,
102+
DiscoveryAddressUDP6LinkLocal: 1,
103+
DiscoveryAddressUDP6RealmLocal: 255,
104+
DiscoveryAddressUDP6SiteLocal: 255,
105+
}
106+
107+
func getHopLimit(addr string, desiredHopLimit int) int {
108+
if desiredHopLimit > 0 {
109+
return desiredHopLimit
110+
}
111+
if v, ok := defaultHopLimit[addr]; ok {
112+
return v
113+
}
114+
return 1
115+
}
116+
92117
// DialDiscoveryAddresses connects to discovery endpoints.
93118
func DialDiscoveryAddresses(ctx context.Context, cfg DiscoveryConfiguration, errors func(error)) ([]*DiscoveryClient, error) {
94119
v, ok := ctx.Deadline()
@@ -105,15 +130,23 @@ func DialDiscoveryAddresses(ctx context.Context, cfg DiscoveryConfiguration, err
105130
msgIDudp6 := msgIDudp4 + ^uint16(0)/2
106131

107132
for _, address := range cfg.MulticastAddressUDP4 {
108-
c, err := newDiscoveryClient("udp4", address, msgIDudp4, timeout, errors, cfg.MulticastOptions)
133+
multicastOptions := []net.MulticastOption{
134+
net.WithMulticastHoplimit(getHopLimit(address, cfg.MulticastHopLimit)),
135+
}
136+
multicastOptions = append(multicastOptions, cfg.MulticastOptions...)
137+
c, err := newDiscoveryClient("udp4", address, msgIDudp4, timeout, errors, multicastOptions)
109138
if err != nil {
110139
errors(err)
111140
continue
112141
}
113142
out = append(out, c)
114143
}
115144
for _, address := range cfg.MulticastAddressUDP6 {
116-
c, err := newDiscoveryClient("udp6", address, msgIDudp6, timeout, errors, cfg.MulticastOptions)
145+
multicastOptions := []net.MulticastOption{
146+
net.WithMulticastHoplimit(getHopLimit(address, cfg.MulticastHopLimit)),
147+
}
148+
multicastOptions = append(multicastOptions, cfg.MulticastOptions...)
149+
c, err := newDiscoveryClient("udp6", address, msgIDudp6, timeout, errors, multicastOptions)
117150
if err != nil {
118151
errors(err)
119152
continue

0 commit comments

Comments
 (0)