ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/loops/ExchangeLoops.java
(Generate patch)

Comparing jsr166/src/test/loops/ExchangeLoops.java (file contents):
Revision 1.1 by dl, Mon May 2 19:19:38 2005 UTC vs.
Revision 1.2 by dl, Mon Feb 13 12:39:23 2006 UTC

# Line 1 | Line 1
1   /*
2 < * @test
3 < * @summary checks to make sure a pipeline of exchangers passes data.
4 < */
5 < /*
6 < * Written by Doug Lea with assistance from members of JCP JSR-166
7 < * Expert Group and released to the public domain. Use, modify, and
8 < * redistribute this code in any way without acknowledgement.
2 > * Written by Bill Scherer and Doug Lea with assistance from members
3 > * of JCP JSR-166 Expert Group and released to the public domain. Use,
4 > * modify, and redistribute this code in any way without
5 > * acknowledgement.
6   */
7  
8   import java.util.concurrent.*;
9 + import java.util.concurrent.atomic.*;
10 + import java.util.concurrent.locks.*;
11  
12   public class ExchangeLoops {
13 <    static final ExecutorService pool = Executors.newCachedThreadPool();
15 <    static boolean print = false;
13 >    static final int NCPUS = Runtime.getRuntime().availableProcessors();
14  
15 <    static class Int {
16 <        public int value;
19 <        Int(int i) { value = i; }
20 <    }
21 <    
15 >    static final int  DEFAULT_THREADS = NCPUS + 2;
16 >    static final long DEFAULT_TRIAL_MILLIS   = 10000;
17  
18      public static void main(String[] args) throws Exception {
19 <        int maxStages = 100;
20 <        int iters = 100000;
19 >        int maxThreads = DEFAULT_THREADS;
20 >        long trialMillis = DEFAULT_TRIAL_MILLIS;
21 >        int nReps = 3;
22 >
23 >        // Parse and check args
24 >        int argc = 0;
25 >        while (argc < args.length) {
26 >            String option = args[argc++];
27 >            if (option.equals("-t"))
28 >                trialMillis = Integer.parseInt(args[argc]);
29 >            else if (option.equals("-r"))
30 >                nReps = Integer.parseInt(args[argc]);
31 >            else
32 >                maxThreads = Integer.parseInt(option);
33 >            argc++;
34 >        }
35  
36 <        if (args.length > 0)
37 <            maxStages = Integer.parseInt(args[0]);
36 >        // Display runtime parameters
37 >        System.out.print("ExchangeTest");
38 >        System.out.print(" -t " + trialMillis);
39 >        System.out.print(" -r " + nReps);
40 >        System.out.print(" max threads " + maxThreads);
41 >        System.out.println();
42 >        long warmupTime = 2000;
43 >        long sleepTime = 100;
44 >        int nw = maxThreads >= 3? 3 : 2;
45 >
46 >        System.out.println("Warmups..");
47 >        oneRun(3, warmupTime);
48 >        Thread.sleep(sleepTime);
49 >
50 >        for (int i = maxThreads; i >= 2; i -= 1) {
51 >            oneRun(i, warmupTime++);
52 >            //            System.gc();
53 >            Thread.sleep(sleepTime);
54 >        }
55  
56 <        print = false;
57 <        System.out.println("Warmup...");
58 <        oneRun(2, 100000);
33 <        print = true;
34 <
35 <        for (int i = 2; i <= maxStages; i += (i+1) >>> 1) {
36 <            System.out.print("Threads: " + i + "\t: ");
37 <            oneRun(i, iters);
38 <        }
39 <        pool.shutdown();
40 <   }
41 <
42 <    static class Stage implements Runnable {
43 <        final int iters;
44 <        final Exchanger<Int> left;
45 <        final Exchanger<Int> right;
46 <        final CyclicBarrier barrier;
47 <        volatile int result;
48 <        Stage (Exchanger<Int> left,
49 <               Exchanger<Int> right,
50 <               CyclicBarrier b, int iters) {
51 <            this.left = left;
52 <            this.right = right;
53 <            barrier = b;
54 <            this.iters = iters;
56 >        /*
57 >        for (int i = maxThreads; i >= 2; i -= 1) {
58 >            oneRun(i, warmupTime++);
59          }
60 +        */
61  
62 <        public void run() {
63 <            try {
64 <                barrier.await();
65 <                Int item = new Int(hashCode());
66 <                for (int i = 0; i < iters; ++i) {
67 <                    if (left != null) {
63 <                        item.value = LoopHelpers.compute1(item.value);
64 <                        Int other = left.exchange(item);
65 <                        if (other == item || other == null)
66 <                            throw new Error("Failed Exchange");
67 <                        item = other;
68 <
69 <                    }
70 <                    if (right != null) {
71 <                        item.value = LoopHelpers.compute2(item.value);
72 <                        Int other = right.exchange(item);
73 <                        if (other == item || other == null)
74 <                            throw new Error("Failed Exchange");
75 <                        item = other;
76 <                    }
77 <                }
78 <                barrier.await();
79 <                
62 >        for (int j = 0; j < nReps; ++j) {
63 >            System.out.println("Trial: " + j);
64 >            for (int i = 2; i <= maxThreads; i += 2) {
65 >                oneRun(i, trialMillis);
66 >                //                System.gc();
67 >                Thread.sleep(sleepTime);
68              }
69 <            catch (Exception ie) {
70 <                ie.printStackTrace();
71 <                return;
69 >            for (int i = maxThreads; i >= 2; i -= 2) {
70 >                oneRun(i, trialMillis);
71 >                //                System.gc();
72 >                Thread.sleep(sleepTime);
73              }
74 +            Thread.sleep(sleepTime);
75          }
76 +
77 +
78      }
79  
80 <    static void oneRun(int nthreads, int iters) throws Exception {
81 <        LoopHelpers.BarrierTimer timer = new LoopHelpers.BarrierTimer();
82 <        CyclicBarrier barrier = new CyclicBarrier(nthreads + 1, timer);
83 <        Exchanger<Int> l = null;
84 <        Exchanger<Int> r = new Exchanger<Int>();
85 <        for (int i = 0; i < nthreads; ++i) {
86 <            pool.execute(new Stage(l, r, barrier, iters));
87 <            l = r;
88 <            r = (i+2 < nthreads) ? new Exchanger<Int>() : null;
89 <        }
90 <        barrier.await();
91 <        barrier.await();
92 <        long time = timer.getTime();
93 <        if (print)
94 <            System.out.println(LoopHelpers.rightJustify(time / (iters * nthreads + iters * (nthreads-2))) + " ns per transfer");
80 >    static void oneRun(int nThreads, long trialMillis) throws Exception {
81 >        System.out.printf("%4d threads", nThreads);
82 >        System.out.printf("%9dms", trialMillis);
83 >        Exchanger x = new Exchanger();
84 >        Runner[] runners = new Runner[nThreads];
85 >        Thread[] threads = new Thread[nThreads];
86 >        for (int i = 0; i < nThreads; ++i) {
87 >            runners[i] = new Runner(x);
88 >            threads[i] = new Thread(runners[i]);
89 >            //            int h = System.identityHashCode(threads[i]);
90 >            //            h ^= h << 1;
91 >            //            h ^= h >>> 3;
92 >            //            h ^= h << 10;
93 >            //            System.out.printf("%10x\n", h);
94 >        }
95 >
96 >        long startTime = System.nanoTime();
97 >        for (int i = 0; i < nThreads; ++i) {
98 >            threads[i].start();
99 >        }
100 >        Thread.sleep(trialMillis);
101 >        for (int i = 0; i < nThreads; ++i)
102 >            threads[i].interrupt();
103 >        long elapsed = System.nanoTime() - startTime;
104 >        for (int i = 0; i < nThreads; ++i)
105 >            threads[i].join();
106 >        int iters = 1;
107 >        //        System.out.println();
108 >        for (int i = 0; i < nThreads; ++i) {
109 >            int ipr = runners[i].iters;
110 >            //            System.out.println(ipr);
111 >            iters += ipr;
112 >        }
113 >        long rate = iters * 1000L * 1000L * 1000L / elapsed;
114 >        long npt = elapsed / iters;
115 >        System.out.printf("%9d it/s ", rate);
116 >        System.out.printf("%9d ns/it", npt);
117 >        System.out.println();
118 >        //        x.printStats();
119      }
120 +      
121 +    static final class Runner implements Runnable {
122 +        final Exchanger exchanger;
123 +        final Object mine = new Integer(2688);
124 +        volatile int iters;
125 +        Runner(Exchanger x) { this.exchanger = x; }
126  
127 +        public void run() {
128 +            Exchanger x = exchanger;
129 +            Object m = mine;
130 +            int i = 0;
131 +            try {
132 +                for (;;) {
133 +                    Object e = x.exchange(m);
134 +                    if (e == null || e == m)
135 +                        throw new Error();
136 +                    m = e;
137 +                    ++i;
138 +                }
139 +            } catch (InterruptedException ie) {
140 +                iters = i;
141 +            }
142 +        }
143 +    }
144   }
145 +        

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines