1/*
2 * Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24/* @test
25 * @bug 4669040 8130394
26 * @summary Test DatagramChannel subsequent receives with no datagram ready
27 * @author Mike McCloskey
28 */
29
30import java.io.IOException;
31import java.io.PrintStream;
32import java.net.InetAddress;
33import java.net.InetSocketAddress;
34import java.net.SocketAddress;
35import java.nio.ByteBuffer;
36import java.nio.ByteOrder;
37import java.nio.channels.DatagramChannel;
38
39public class Sender {
40
41    static PrintStream log = System.err;
42    static volatile SocketAddress clientISA = null;
43
44    public static void main(String[] args) throws Exception {
45        test();
46    }
47
48    static void test() throws Exception {
49        Server server = new Server();
50        Client client = new Client(server.port());
51
52        Thread serverThread = new Thread(server);
53        serverThread.start();
54
55        Thread clientThread = new Thread(client);
56        clientThread.start();
57
58        serverThread.join();
59        clientThread.join();
60
61        server.throwException();
62        client.throwException();
63    }
64
65    public static class Client implements Runnable {
66        final int port;
67        Exception e = null;
68
69        Client(int port) {
70            this.port = port;
71        }
72
73        void throwException() throws Exception {
74            if (e != null)
75                throw e;
76        }
77
78        public void run() {
79            try {
80                DatagramChannel dc = DatagramChannel.open();
81                ByteBuffer bb = ByteBuffer.allocateDirect(12);
82                bb.order(ByteOrder.BIG_ENDIAN);
83                bb.putInt(1).putLong(1);
84                bb.flip();
85                InetAddress address = InetAddress.getLocalHost();
86                InetSocketAddress isa = new InetSocketAddress(address, port);
87                dc.connect(isa);
88                clientISA = dc.getLocalAddress();
89                dc.write(bb);
90            } catch (Exception ex) {
91                e = ex;
92            }
93        }
94    }
95
96    public static class Server implements Runnable {
97        final DatagramChannel dc;
98        Exception e = null;
99
100        Server() throws IOException {
101            dc = DatagramChannel.open().bind(new InetSocketAddress(0));
102        }
103
104        int port() {
105            return dc.socket().getLocalPort();
106        }
107
108        void throwException() throws Exception {
109            if (e != null)
110                throw e;
111        }
112
113        void showBuffer(String s, ByteBuffer bb) {
114            log.println(s);
115            bb.rewind();
116            for (int i=0; i<bb.limit(); i++) {
117                byte element = bb.get();
118                log.print(element);
119            }
120            log.println();
121        }
122
123        public void run() {
124            SocketAddress sa = null;
125
126
127            try {
128                ByteBuffer bb = ByteBuffer.allocateDirect(12);
129                bb.clear();
130                // Get the one valid datagram
131                dc.configureBlocking(false);
132                while (sa == null) {
133                    sa = dc.receive(bb);
134                    if (sa != null && clientISA != null && !clientISA.equals(sa)) {
135                        log.println("Ignore a possible stray diagram from " + sa);
136                        sa = null;
137                    }
138                }
139                showBuffer("Received:", bb);
140                sa = null;
141                for (int i=0; i<100; i++) {
142                    bb.clear();
143                    sa = dc.receive(bb);
144                    if (sa != null)
145                        throw new RuntimeException("Test failed");
146                }
147                dc.close();
148            } catch (Exception ex) {
149                e = ex;
150            }
151        }
152    }
153
154}
155