Java Reference
In-Depth Information
not have to use it thereafter, and you don't have to use it all in Java 7 and later. Nor do
you ever use
DatagramPacket
. Instead, you read and write byte buffers, just as you do
with a
SocketChannel
.
Opening a socket
The
java.nio.channels.DatagramChannel
class does not have any public construcā
tors. Instead, you create a new
DatagramChannel
object using the static
open()
method
For example:
DatagramChannel channel = DatagramChannel.open();
This channel is not initially bound to any port. To bind it, you access the channel's peer
DatagramSocket
object using the
socket()
method. For example, this binds a channel
to port 3141:
SocketAddress address = new InetSocketAddress(3141);
DatagramSocket socket = channel.socket();
socket.bind(address);
Java 7 adds a convenient
bind()
method directly to
DatagramChannel
, so you don't have
to use a
DatagramSocket
at all. For example:
SocketAddress address = new InetSocketAddress(3141);
channel.bind(address);
Receiving
The
receive()
method reads one datagram packet from the channel into a
ByteBuffer
.
It returns the address of the host that sent the packet:
public
SocketAddress
receive
(
ByteBuffer
dst
)
throws
IOException
If the channel is blocking (the default), this method will not return until a packet has
been read. If the channel is nonblocking, this method will immediately return null if no
packet is available to read.
If the datagram packet has more data than the buffer can hold,
the extra data is thrown
away with no notification of the problem
. You do not receive a
BufferOverflowExcep
tion
or anything similar. Again you see that UDP is unreliable. This behavior introduces
an additional layer of unreliability into the system. The data can arrive safely from the
network and still be lost inside your own program.
Using this method, you can reimplement the discard server to log the host sending the
data as well as the data sent.
Example 12-15
demonstrates. It avoids the potential loss of
data by using a buffer that's big enough to hold any UDP packet and clearing it before
it's used again.
Example 12-15. A UDPDiscardServer based on channels
import
java.io.*
;
import
java.net.*
;