blob: e1ae8167b3a4bad4d9bb1feeb4a92ecd0ed341c6 [file] [log] [blame]
David K. Bainbridge215e0242017-09-05 23:18:24 -07001// Copyright 2012 The Go Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style
3// license that can be found in the LICENSE file.
4
5// +build darwin dragonfly freebsd linux netbsd openbsd solaris
6
7package ipv4
8
9import (
10 "unsafe"
11
12 "golang.org/x/net/internal/iana"
13 "golang.org/x/net/internal/socket"
14)
15
16func setControlMessage(c *socket.Conn, opt *rawOpt, cf ControlFlags, on bool) error {
17 opt.Lock()
18 defer opt.Unlock()
19 if so, ok := sockOpts[ssoReceiveTTL]; ok && cf&FlagTTL != 0 {
20 if err := so.SetInt(c, boolint(on)); err != nil {
21 return err
22 }
23 if on {
24 opt.set(FlagTTL)
25 } else {
26 opt.clear(FlagTTL)
27 }
28 }
29 if so, ok := sockOpts[ssoPacketInfo]; ok {
30 if cf&(FlagSrc|FlagDst|FlagInterface) != 0 {
31 if err := so.SetInt(c, boolint(on)); err != nil {
32 return err
33 }
34 if on {
35 opt.set(cf & (FlagSrc | FlagDst | FlagInterface))
36 } else {
37 opt.clear(cf & (FlagSrc | FlagDst | FlagInterface))
38 }
39 }
40 } else {
41 if so, ok := sockOpts[ssoReceiveDst]; ok && cf&FlagDst != 0 {
42 if err := so.SetInt(c, boolint(on)); err != nil {
43 return err
44 }
45 if on {
46 opt.set(FlagDst)
47 } else {
48 opt.clear(FlagDst)
49 }
50 }
51 if so, ok := sockOpts[ssoReceiveInterface]; ok && cf&FlagInterface != 0 {
52 if err := so.SetInt(c, boolint(on)); err != nil {
53 return err
54 }
55 if on {
56 opt.set(FlagInterface)
57 } else {
58 opt.clear(FlagInterface)
59 }
60 }
61 }
62 return nil
63}
64
65func marshalTTL(b []byte, cm *ControlMessage) []byte {
66 m := socket.ControlMessage(b)
67 m.MarshalHeader(iana.ProtocolIP, sysIP_RECVTTL, 1)
68 return m.Next(1)
69}
70
71func parseTTL(cm *ControlMessage, b []byte) {
72 cm.TTL = int(*(*byte)(unsafe.Pointer(&b[:1][0])))
73}