OSDN Git Service

new repo
[bytom/vapor.git] / vendor / golang.org / x / net / route / route_classic.go
1 // Copyright 2016 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 netbsd
6
7 package route
8
9 import "syscall"
10
11 func (m *RouteMessage) marshal() ([]byte, error) {
12         w, ok := wireFormats[m.Type]
13         if !ok {
14                 return nil, errUnsupportedMessage
15         }
16         l := w.bodyOff + addrsSpace(m.Addrs)
17         b := make([]byte, l)
18         nativeEndian.PutUint16(b[:2], uint16(l))
19         if m.Version == 0 {
20                 b[2] = sysRTM_VERSION
21         } else {
22                 b[2] = byte(m.Version)
23         }
24         b[3] = byte(m.Type)
25         nativeEndian.PutUint32(b[8:12], uint32(m.Flags))
26         nativeEndian.PutUint16(b[4:6], uint16(m.Index))
27         nativeEndian.PutUint32(b[16:20], uint32(m.ID))
28         nativeEndian.PutUint32(b[20:24], uint32(m.Seq))
29         attrs, err := marshalAddrs(b[w.bodyOff:], m.Addrs)
30         if err != nil {
31                 return nil, err
32         }
33         if attrs > 0 {
34                 nativeEndian.PutUint32(b[12:16], uint32(attrs))
35         }
36         return b, nil
37 }
38
39 func (w *wireFormat) parseRouteMessage(typ RIBType, b []byte) (Message, error) {
40         if len(b) < w.bodyOff {
41                 return nil, errMessageTooShort
42         }
43         l := int(nativeEndian.Uint16(b[:2]))
44         if len(b) < l {
45                 return nil, errInvalidMessage
46         }
47         m := &RouteMessage{
48                 Version: int(b[2]),
49                 Type:    int(b[3]),
50                 Flags:   int(nativeEndian.Uint32(b[8:12])),
51                 Index:   int(nativeEndian.Uint16(b[4:6])),
52                 ID:      uintptr(nativeEndian.Uint32(b[16:20])),
53                 Seq:     int(nativeEndian.Uint32(b[20:24])),
54                 extOff:  w.extOff,
55                 raw:     b[:l],
56         }
57         errno := syscall.Errno(nativeEndian.Uint32(b[28:32]))
58         if errno != 0 {
59                 m.Err = errno
60         }
61         var err error
62         m.Addrs, err = parseAddrs(uint(nativeEndian.Uint32(b[12:16])), parseKernelInetAddr, b[w.bodyOff:])
63         if err != nil {
64                 return nil, err
65         }
66         return m, nil
67 }