1 /*
2 * Copyright (c) 2005, 2010, 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 */
59 testQueue(new ConcurrentLinkedQueue());
60 testQueue(new LinkedTransferQueue());
61 }
62
63 Random getRandom() {
64 return ThreadLocalRandom.current();
65 }
66
67 void testQueue(final Queue q) throws Throwable {
68 System.out.println(q.getClass().getSimpleName());
69 final long testDurationNanos = testDurationMillis * 1000L * 1000L;
70 final long quittingTimeNanos = System.nanoTime() + testDurationNanos;
71 final long timeoutMillis = 10L * 1000L;
72 final int maxChunkSize = 1042;
73 final int maxQueueSize = 10 * maxChunkSize;
74
75 /** Poor man's bounded buffer. */
76 final AtomicLong approximateCount = new AtomicLong(0L);
77
78 abstract class CheckedThread extends Thread {
79 CheckedThread(String name) {
80 super(name);
81 setDaemon(true);
82 start();
83 }
84 /** Polls for quitting time. */
85 protected boolean quittingTime() {
86 return System.nanoTime() - quittingTimeNanos > 0;
87 }
88 /** Polls occasionally for quitting time. */
89 protected boolean quittingTime(long i) {
90 return (i % 1024) == 0 && quittingTime();
91 }
92 abstract protected void realRun();
93 public void run() {
94 try { realRun(); } catch (Throwable t) { unexpected(t); }
95 }
96 }
97
98 Thread offerer = new CheckedThread("offerer") {
99 protected void realRun() {
100 final long chunkSize = getRandom().nextInt(maxChunkSize) + 2;
101 long c = 0;
102 for (long i = 0; ! quittingTime(i); i++) {
103 if (q.offer(Long.valueOf(c))) {
104 if ((++c % chunkSize) == 0) {
105 approximateCount.getAndAdd(chunkSize);
106 while (approximateCount.get() > maxQueueSize)
107 Thread.yield();
108 }
109 } else {
110 Thread.yield();
111 }}}};
112
113 Thread remover = new CheckedThread("remover") {
114 protected void realRun() {
115 final long chunkSize = getRandom().nextInt(maxChunkSize) + 2;
116 long c = 0;
117 for (long i = 0; ! quittingTime(i); i++) {
118 if (q.remove(Long.valueOf(c))) {
119 if ((++c % chunkSize) == 0) {
120 approximateCount.getAndAdd(-chunkSize);
121 }
122 } else {
123 Thread.yield();
124 }
125 }
126 q.clear();
127 approximateCount.set(0); // Releases waiting offerer thread
128 }};
129
130 Thread scanner = new CheckedThread("scanner") {
131 protected void realRun() {
132 final Random rnd = getRandom();
133 while (! quittingTime()) {
134 switch (rnd.nextInt(3)) {
135 case 0: checkNotContainsNull(q); break;
136 case 1: q.size(); break;
137 case 2: checkNotContainsNull
138 (Arrays.asList(q.toArray(new Long[0])));
139 break;
140 }
141 Thread.yield();
142 }}};
143
144 for (Thread thread : new Thread[] { offerer, remover, scanner }) {
145 thread.join(timeoutMillis + testDurationMillis);
146 if (thread.isAlive()) {
147 System.err.printf("Hung thread: %s%n", thread.getName());
148 failed++;
149 for (StackTraceElement e : thread.getStackTrace())
150 System.err.println(e);
151 // Kludge alert
152 thread.stop();
153 thread.join(timeoutMillis);
154 }
155 }
156 }
157
158 //--------------------- Infrastructure ---------------------------
159 volatile int passed = 0, failed = 0;
160 void pass() {passed++;}
161 void fail() {failed++; Thread.dumpStack();}
162 void fail(String msg) {System.err.println(msg); fail();}
163 void unexpected(Throwable t) {failed++; t.printStackTrace();}
164 void check(boolean cond) {if (cond) pass(); else fail();}
165 void equal(Object x, Object y) {
166 if (x == null ? y == null : x.equals(y)) pass();
167 else fail(x + " not equal to " + y);}
168 public static void main(String[] args) throws Throwable {
169 new OfferRemoveLoops(args).instanceMain(args);}
170 public void instanceMain(String[] args) throws Throwable {
171 try {test(args);} catch (Throwable t) {unexpected(t);}
172 System.out.printf("%nPassed = %d, failed = %d%n%n", passed, failed);
|
1 /*
2 * Copyright (c) 2005, 2014, 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 */
59 testQueue(new ConcurrentLinkedQueue());
60 testQueue(new LinkedTransferQueue());
61 }
62
63 Random getRandom() {
64 return ThreadLocalRandom.current();
65 }
66
67 void testQueue(final Queue q) throws Throwable {
68 System.out.println(q.getClass().getSimpleName());
69 final long testDurationNanos = testDurationMillis * 1000L * 1000L;
70 final long quittingTimeNanos = System.nanoTime() + testDurationNanos;
71 final long timeoutMillis = 10L * 1000L;
72 final int maxChunkSize = 1042;
73 final int maxQueueSize = 10 * maxChunkSize;
74
75 /** Poor man's bounded buffer. */
76 final AtomicLong approximateCount = new AtomicLong(0L);
77
78 abstract class CheckedThread extends Thread {
79 protected volatile boolean stopRequest = false;
80
81 CheckedThread(String name) {
82 super(name);
83 setDaemon(true);
84 start();
85 }
86 /** Polls for quitting time. */
87 protected boolean quittingTime() {
88 return System.nanoTime() - quittingTimeNanos > 0;
89 }
90 /** Polls occasionally for quitting time. */
91 protected boolean quittingTime(long i) {
92 return stopRequest || quittingTime() && (i % 1024 == 0 || i < 1024);
93 }
94 protected void giveupCPU(){
95 try {
96 Thread.sleep(0L);
97 } catch (InterruptedException ignore) {}
98 }
99 abstract protected void realRun();
100 public void run() {
101 try { realRun(); } catch (Throwable t) { unexpected(t); }
102 }
103 public void stopThread() {
104 stopRequest = true;
105 }
106 }
107
108 CheckedThread offerer = new CheckedThread("offerer") {
109 protected void realRun() {
110 final long chunkSize = getRandom().nextInt(maxChunkSize) + 2;
111 long c = 0;
112 for (long i = 0; ! quittingTime(i); i++) {
113 if (q.offer(Long.valueOf(c))) {
114 if ((++c % chunkSize) == 0) {
115 approximateCount.getAndAdd(chunkSize);
116 while (approximateCount.get() > maxQueueSize)
117 giveupCPU();
118 }
119 } else {
120 giveupCPU();
121 }}}};
122
123 CheckedThread remover = new CheckedThread("remover") {
124 protected void realRun() {
125 final long chunkSize = getRandom().nextInt(maxChunkSize) + 2;
126 long c = 0;
127 for (long i = 0; ! quittingTime(i); i++) {
128 if (q.remove(Long.valueOf(c))) {
129 if ((++c % chunkSize) == 0) {
130 approximateCount.getAndAdd(-chunkSize);
131 }
132 } else {
133 giveupCPU();
134 }
135 }
136 q.clear();
137 approximateCount.set(0); // Releases waiting offerer thread
138 }};
139
140 CheckedThread scanner = new CheckedThread("scanner") {
141 protected void realRun() {
142 final Random rnd = getRandom();
143 while (! quittingTime()) {
144 switch (rnd.nextInt(3)) {
145 case 0: checkNotContainsNull(q); break;
146 case 1: q.size(); break;
147 case 2: checkNotContainsNull
148 (Arrays.asList(q.toArray(new Long[0])));
149 break;
150 }
151 giveupCPU();
152 }}};
153
154 for (CheckedThread thread : new CheckedThread[] { offerer, remover, scanner }) {
155 thread.join(timeoutMillis + testDurationMillis);
156 if (thread.isAlive()) {
157 System.err.printf("Hung thread: %s%n", thread.getName());
158 failed++;
159 for (StackTraceElement e : thread.getStackTrace())
160 System.err.println(e);
161 // Kludge alert
162 thread.stopThread();
163 thread.join(timeoutMillis);
164 }
165 }
166 }
167
168 //--------------------- Infrastructure ---------------------------
169 volatile int passed = 0, failed = 0;
170 void pass() {passed++;}
171 void fail() {failed++; Thread.dumpStack();}
172 void fail(String msg) {System.err.println(msg); fail();}
173 void unexpected(Throwable t) {failed++; t.printStackTrace();}
174 void check(boolean cond) {if (cond) pass(); else fail();}
175 void equal(Object x, Object y) {
176 if (x == null ? y == null : x.equals(y)) pass();
177 else fail(x + " not equal to " + y);}
178 public static void main(String[] args) throws Throwable {
179 new OfferRemoveLoops(args).instanceMain(args);}
180 public void instanceMain(String[] args) throws Throwable {
181 try {test(args);} catch (Throwable t) {unexpected(t);}
182 System.out.printf("%nPassed = %d, failed = %d%n%n", passed, failed);
|