Skip to content

Commit 30b7837

Browse files
committed
Unit test
1 parent 755995b commit 30b7837

File tree

2 files changed

+229
-162
lines changed

2 files changed

+229
-162
lines changed
Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
// SPDX-FileCopyrightText: 2020 C. Ramakrishnan / Illposed Software
2+
// SPDX-FileCopyrightText: 2021 Robin Vobruba <hoijui.quaero@gmail.com>
3+
//
4+
// SPDX-License-Identifier: BSD-3-Clause
5+
6+
package com.illposed.osc.transport.udp;
7+
8+
import com.illposed.osc.OSCSerializeException;
9+
import com.illposed.osc.transport.OSCPort;
10+
11+
import java.io.IOException;
12+
import java.net.Inet4Address;
13+
import java.net.Inet6Address;
14+
import java.net.InetAddress;
15+
import java.net.InetSocketAddress;
16+
import java.net.SocketAddress;
17+
import java.net.StandardProtocolFamily;
18+
import java.net.StandardSocketOptions;
19+
import java.nio.ByteBuffer;
20+
import java.nio.channels.DatagramChannel;
21+
import java.util.Random;
22+
23+
import org.junit.jupiter.api.Assertions;
24+
import org.junit.jupiter.api.Test;
25+
import org.slf4j.Logger;
26+
import org.slf4j.LoggerFactory;
27+
28+
public class DatagramChannelTest {
29+
30+
private static final long WAIT_FOR_SOCKET_CLOSE = 30;
31+
32+
private final Logger log = LoggerFactory.getLogger(DatagramChannelTest.class);
33+
34+
@Test
35+
public void readWriteReadData400() throws Exception {
36+
readWriteReadData(400);
37+
}
38+
39+
@Test
40+
public void readWriteReadData600() throws Exception {
41+
// common minimal maximum UDP buffer size (MTU) is 5xx Bytes
42+
readWriteReadData(600);
43+
}
44+
45+
@Test
46+
public void readWriteReadData1400() throws Exception {
47+
readWriteReadData(1400);
48+
}
49+
50+
@Test
51+
public void readWriteReadData2000() throws Exception {
52+
// default maximum UDP buffer size (MTU) is ~1500 Bytes
53+
readWriteReadData(2000);
54+
}
55+
56+
@Test
57+
public void readWriteReadData50000() throws Exception {
58+
readWriteReadData(50000);
59+
}
60+
61+
@Test
62+
public void readWriteReadData70000() throws Exception {
63+
// theoretical maximum UDP buffer size (MTU) is 2^16 - 1 = 65535 Bytes
64+
65+
Assertions.assertThrows(
66+
IOException.class,
67+
() -> readWriteReadData(70000)
68+
);
69+
}
70+
71+
private void readWriteReadData(final int sizeInBytes)
72+
throws Exception
73+
{
74+
final int portSender = 6666;
75+
final int portReceiver = 7777;
76+
77+
final SocketAddress senderSocket = new InetSocketAddress(InetAddress.getLocalHost(), portSender);
78+
final SocketAddress receiverSocket = new InetSocketAddress(InetAddress.getLocalHost(), portReceiver);
79+
80+
81+
DatagramChannel senderChannel = null;
82+
DatagramChannel receiverChannel = null;
83+
try {
84+
senderChannel = DatagramChannel.open();
85+
senderChannel.socket().bind(senderSocket);
86+
senderChannel.socket().setReuseAddress(true);
87+
senderChannel.socket().setSendBufferSize(UDPTransport.BUFFER_SIZE);
88+
89+
receiverChannel = DatagramChannel.open();
90+
receiverChannel.socket().bind(receiverSocket);
91+
receiverChannel.socket().setReuseAddress(true);
92+
93+
senderChannel.connect(receiverSocket);
94+
receiverChannel.connect(senderSocket);
95+
96+
final byte[] sourceArray = new byte[sizeInBytes];
97+
final byte[] targetArray = new byte[sizeInBytes];
98+
99+
new Random().nextBytes(sourceArray);
100+
101+
readWriteReadData(senderChannel, sourceArray, receiverChannel, targetArray, sizeInBytes);
102+
} finally {
103+
if (receiverChannel != null) {
104+
try {
105+
receiverChannel.close();
106+
} catch (final IOException ex) {
107+
log.error("Failed to close test OSC in channel", ex);
108+
}
109+
}
110+
if (senderChannel != null) {
111+
try {
112+
senderChannel.close();
113+
} catch (final IOException ex) {
114+
log.error("Failed to close test OSC out channel", ex);
115+
}
116+
}
117+
118+
// wait a bit after closing the receiver,
119+
// because (some) operating systems need some time
120+
// to actually close the underlying socket
121+
Thread.sleep(WAIT_FOR_SOCKET_CLOSE);
122+
}
123+
}
124+
125+
private void readWriteReadData(
126+
final DatagramChannel sender,
127+
final byte[] sourceArray,
128+
final DatagramChannel receiver,
129+
byte[] targetArray,
130+
final int dataSize)
131+
throws IOException
132+
{
133+
// write
134+
final ByteBuffer sourceBuf = ByteBuffer.wrap(sourceArray);
135+
Assertions.assertEquals(dataSize, sender.write(sourceBuf));
136+
137+
// read
138+
final ByteBuffer targetBuf = ByteBuffer.wrap(targetArray);
139+
140+
int count;
141+
int total = 0;
142+
final long beginTime = System.currentTimeMillis();
143+
while ((total < dataSize) && (((count = receiver.read(targetBuf))) != -1)) {
144+
total = total + count;
145+
// 3s timeout to avoid dead loop
146+
if ((System.currentTimeMillis() - beginTime) > 3000) {
147+
break;
148+
}
149+
}
150+
151+
Assertions.assertEquals(dataSize, total);
152+
Assertions.assertEquals(targetBuf.position(), total);
153+
targetBuf.flip();
154+
targetArray = targetBuf.array();
155+
for (int i = 0; i < targetArray.length; i++) {
156+
Assertions.assertEquals(sourceArray[i], targetArray[i]);
157+
}
158+
}
159+
160+
@Test
161+
public void testBindChannel() throws Exception {
162+
final InetSocketAddress bindAddress = new InetSocketAddress(OSCPort.defaultSCOSCPort());
163+
164+
final DatagramChannel channel;
165+
if (bindAddress.getAddress() instanceof Inet4Address) {
166+
channel = DatagramChannel.open(StandardProtocolFamily.INET);
167+
} else if (bindAddress.getAddress() instanceof Inet6Address) {
168+
channel = DatagramChannel.open(StandardProtocolFamily.INET6);
169+
} else {
170+
throw new IllegalArgumentException(
171+
"Unknown address type: "
172+
+ bindAddress.getAddress().getClass().getCanonicalName());
173+
}
174+
channel.setOption(StandardSocketOptions.SO_REUSEADDR, true);
175+
channel.socket().bind(bindAddress);
176+
177+
Assertions.assertEquals(bindAddress, channel.getLocalAddress());
178+
}
179+
}

0 commit comments

Comments
 (0)