OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libgo/] [go/] [net/] [iprawsock_posix.go] - Blame information for rev 747

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 747 jeremybenn
// Copyright 2010 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 freebsd linux netbsd openbsd windows
6
 
7
// (Raw) IP sockets
8
 
9
package net
10
 
11
import (
12
        "os"
13
        "syscall"
14
        "time"
15
)
16
 
17
func sockaddrToIP(sa syscall.Sockaddr) Addr {
18
        switch sa := sa.(type) {
19
        case *syscall.SockaddrInet4:
20
                return &IPAddr{sa.Addr[0:]}
21
        case *syscall.SockaddrInet6:
22
                return &IPAddr{sa.Addr[0:]}
23
        }
24
        return nil
25
}
26
 
27
func (a *IPAddr) family() int {
28
        if a == nil || len(a.IP) <= IPv4len {
29
                return syscall.AF_INET
30
        }
31
        if a.IP.To4() != nil {
32
                return syscall.AF_INET
33
        }
34
        return syscall.AF_INET6
35
}
36
 
37
func (a *IPAddr) sockaddr(family int) (syscall.Sockaddr, error) {
38
        return ipToSockaddr(family, a.IP, 0)
39
}
40
 
41
func (a *IPAddr) toAddr() sockaddr {
42
        if a == nil { // nil *IPAddr
43
                return nil // nil interface
44
        }
45
        return a
46
}
47
 
48
// IPConn is the implementation of the Conn and PacketConn
49
// interfaces for IP network connections.
50
type IPConn struct {
51
        fd *netFD
52
}
53
 
54
func newIPConn(fd *netFD) *IPConn { return &IPConn{fd} }
55
 
56
func (c *IPConn) ok() bool { return c != nil && c.fd != nil }
57
 
58
// Implementation of the Conn interface - see Conn for documentation.
59
 
60
// Read implements the Conn Read method.
61
func (c *IPConn) Read(b []byte) (int, error) {
62
        n, _, err := c.ReadFrom(b)
63
        return n, err
64
}
65
 
66
// Write implements the Conn Write method.
67
func (c *IPConn) Write(b []byte) (int, error) {
68
        if !c.ok() {
69
                return 0, os.EINVAL
70
        }
71
        return c.fd.Write(b)
72
}
73
 
74
// Close closes the IP connection.
75
func (c *IPConn) Close() error {
76
        if !c.ok() {
77
                return os.EINVAL
78
        }
79
        err := c.fd.Close()
80
        c.fd = nil
81
        return err
82
}
83
 
84
// LocalAddr returns the local network address.
85
func (c *IPConn) LocalAddr() Addr {
86
        if !c.ok() {
87
                return nil
88
        }
89
        return c.fd.laddr
90
}
91
 
92
// RemoteAddr returns the remote network address, a *IPAddr.
93
func (c *IPConn) RemoteAddr() Addr {
94
        if !c.ok() {
95
                return nil
96
        }
97
        return c.fd.raddr
98
}
99
 
100
// SetDeadline implements the Conn SetDeadline method.
101
func (c *IPConn) SetDeadline(t time.Time) error {
102
        if !c.ok() {
103
                return os.EINVAL
104
        }
105
        return setDeadline(c.fd, t)
106
}
107
 
108
// SetReadDeadline implements the Conn SetReadDeadline method.
109
func (c *IPConn) SetReadDeadline(t time.Time) error {
110
        if !c.ok() {
111
                return os.EINVAL
112
        }
113
        return setReadDeadline(c.fd, t)
114
}
115
 
116
// SetWriteDeadline implements the Conn SetWriteDeadline method.
117
func (c *IPConn) SetWriteDeadline(t time.Time) error {
118
        if !c.ok() {
119
                return os.EINVAL
120
        }
121
        return setWriteDeadline(c.fd, t)
122
}
123
 
124
// SetReadBuffer sets the size of the operating system's
125
// receive buffer associated with the connection.
126
func (c *IPConn) SetReadBuffer(bytes int) error {
127
        if !c.ok() {
128
                return os.EINVAL
129
        }
130
        return setReadBuffer(c.fd, bytes)
131
}
132
 
133
// SetWriteBuffer sets the size of the operating system's
134
// transmit buffer associated with the connection.
135
func (c *IPConn) SetWriteBuffer(bytes int) error {
136
        if !c.ok() {
137
                return os.EINVAL
138
        }
139
        return setWriteBuffer(c.fd, bytes)
140
}
141
 
142
// IP-specific methods.
143
 
144
// ReadFromIP reads a IP packet from c, copying the payload into b.
145
// It returns the number of bytes copied into b and the return address
146
// that was on the packet.
147
//
148
// ReadFromIP can be made to time out and return an error with
149
// Timeout() == true after a fixed time limit; see SetDeadline and
150
// SetReadDeadline.
151
func (c *IPConn) ReadFromIP(b []byte) (int, *IPAddr, error) {
152
        if !c.ok() {
153
                return 0, nil, os.EINVAL
154
        }
155
        // TODO(cw,rsc): consider using readv if we know the family
156
        // type to avoid the header trim/copy
157
        var addr *IPAddr
158
        n, sa, err := c.fd.ReadFrom(b)
159
        switch sa := sa.(type) {
160
        case *syscall.SockaddrInet4:
161
                addr = &IPAddr{sa.Addr[0:]}
162
                if len(b) >= IPv4len { // discard ipv4 header
163
                        hsize := (int(b[0]) & 0xf) * 4
164
                        copy(b, b[hsize:])
165
                        n -= hsize
166
                }
167
        case *syscall.SockaddrInet6:
168
                addr = &IPAddr{sa.Addr[0:]}
169
        }
170
        return n, addr, err
171
}
172
 
173
// ReadFrom implements the PacketConn ReadFrom method.
174
func (c *IPConn) ReadFrom(b []byte) (int, Addr, error) {
175
        if !c.ok() {
176
                return 0, nil, os.EINVAL
177
        }
178
        n, uaddr, err := c.ReadFromIP(b)
179
        return n, uaddr.toAddr(), err
180
}
181
 
182
// WriteToIP writes a IP packet to addr via c, copying the payload from b.
183
//
184
// WriteToIP can be made to time out and return
185
// an error with Timeout() == true after a fixed time limit;
186
// see SetDeadline and SetWriteDeadline.
187
// On packet-oriented connections, write timeouts are rare.
188
func (c *IPConn) WriteToIP(b []byte, addr *IPAddr) (int, error) {
189
        if !c.ok() {
190
                return 0, os.EINVAL
191
        }
192
        sa, err := addr.sockaddr(c.fd.family)
193
        if err != nil {
194
                return 0, &OpError{"write", c.fd.net, addr, err}
195
        }
196
        return c.fd.WriteTo(b, sa)
197
}
198
 
199
// WriteTo implements the PacketConn WriteTo method.
200
func (c *IPConn) WriteTo(b []byte, addr Addr) (int, error) {
201
        if !c.ok() {
202
                return 0, os.EINVAL
203
        }
204
        a, ok := addr.(*IPAddr)
205
        if !ok {
206
                return 0, &OpError{"write", c.fd.net, addr, os.EINVAL}
207
        }
208
        return c.WriteToIP(b, a)
209
}
210
 
211
// DialIP connects to the remote address raddr on the network protocol netProto,
212
// which must be "ip", "ip4", or "ip6" followed by a colon and a protocol number or name.
213
func DialIP(netProto string, laddr, raddr *IPAddr) (*IPConn, error) {
214
        net, proto, err := parseDialNetwork(netProto)
215
        if err != nil {
216
                return nil, err
217
        }
218
        switch net {
219
        case "ip", "ip4", "ip6":
220
        default:
221
                return nil, UnknownNetworkError(net)
222
        }
223
        if raddr == nil {
224
                return nil, &OpError{"dial", netProto, nil, errMissingAddress}
225
        }
226
        fd, err := internetSocket(net, laddr.toAddr(), raddr.toAddr(), syscall.SOCK_RAW, proto, "dial", sockaddrToIP)
227
        if err != nil {
228
                return nil, err
229
        }
230
        return newIPConn(fd), nil
231
}
232
 
233
// ListenIP listens for incoming IP packets addressed to the
234
// local address laddr.  The returned connection c's ReadFrom
235
// and WriteTo methods can be used to receive and send IP
236
// packets with per-packet addressing.
237
func ListenIP(netProto string, laddr *IPAddr) (*IPConn, error) {
238
        net, proto, err := parseDialNetwork(netProto)
239
        if err != nil {
240
                return nil, err
241
        }
242
        switch net {
243
        case "ip", "ip4", "ip6":
244
        default:
245
                return nil, UnknownNetworkError(net)
246
        }
247
        fd, err := internetSocket(net, laddr.toAddr(), nil, syscall.SOCK_RAW, proto, "listen", sockaddrToIP)
248
        if err != nil {
249
                return nil, err
250
        }
251
        return newIPConn(fd), nil
252
}
253
 
254
// File returns a copy of the underlying os.File, set to blocking mode.
255
// It is the caller's responsibility to close f when finished.
256
// Closing c does not affect f, and closing f does not affect c.
257
func (c *IPConn) File() (f *os.File, err error) { return c.fd.dup() }

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.