Lines 61-119
public class ObjectMarker
Link Here
|
61 |
|
61 |
|
62 |
public class FjObjectMarker extends RecursiveAction |
62 |
public class FjObjectMarker extends RecursiveAction |
63 |
{ |
63 |
{ |
64 |
final int[] roots; |
64 |
final int position; |
65 |
final boolean[] visited; |
65 |
final boolean[] visited; |
66 |
final IIndexReader.IOne2ManyIndex outbound; |
|
|
67 |
final boolean topLevel; |
66 |
final boolean topLevel; |
68 |
|
67 |
|
69 |
private FjObjectMarker(final int[] roots, final boolean[] visited, final IIndexReader.IOne2ManyIndex outbound, |
68 |
int counter = 0; |
70 |
final boolean topLevel) |
69 |
|
|
|
70 |
private FjObjectMarker(final int position, final boolean[] visited, final boolean topLevel) |
71 |
{ |
71 |
{ |
72 |
this.roots = roots; |
72 |
// for the very root |
|
|
73 |
visited[position] = true; |
74 |
this.position = position; |
73 |
this.visited = visited; |
75 |
this.visited = visited; |
74 |
this.outbound = outbound; |
|
|
75 |
this.topLevel = topLevel; |
76 |
this.topLevel = topLevel; |
76 |
} |
77 |
} |
77 |
|
78 |
|
78 |
public void compute() |
79 |
public void compute() |
79 |
{ |
80 |
{ |
|
|
81 |
if (progressListener.isCanceled()) |
82 |
{ return; } |
83 |
|
84 |
compute(position, LEVELS_RUN_INLINE); |
85 |
|
80 |
if (topLevel) |
86 |
if (topLevel) |
81 |
{ |
87 |
{ |
82 |
// report progress only for top level tasks |
88 |
progressListener.worked(1); |
83 |
progressListener.beginTask(Messages.ObjectMarker_MarkingObjects, roots.length); |
|
|
84 |
compute(roots, LEVELS_RUN_INLINE); |
85 |
progressListener.done(); |
86 |
} else { |
87 |
compute(roots, LEVELS_RUN_INLINE); |
88 |
} |
89 |
} |
89 |
} |
90 |
} |
90 |
|
91 |
|
91 |
void compute(final int[] currentRoots, final int levelsLeft) |
92 |
void compute(final int outboundPosition, final int levelsLeft) |
92 |
{ |
93 |
{ |
93 |
for (int r : currentRoots) |
94 |
final int[] process = outbound.get(outboundPosition); |
|
|
95 |
|
96 |
for (int r : process) |
94 |
{ |
97 |
{ |
95 |
// mark away |
|
|
96 |
if (!visited[r]) |
98 |
if (!visited[r]) |
97 |
{ |
99 |
{ |
98 |
visited[r] = true; |
100 |
visited[r] = true; |
99 |
int[] nextLevel = outbound.get(r); |
|
|
100 |
if (levelsLeft == 0) |
101 |
if (levelsLeft == 0) |
101 |
{ |
102 |
{ |
102 |
new FjObjectMarker(nextLevel, visited, outbound, false).fork(); |
103 |
new FjObjectMarker(r, visited, false).fork(); |
103 |
} |
104 |
} |
104 |
else |
105 |
else |
105 |
{ |
106 |
{ |
106 |
compute(nextLevel, levelsLeft - 1); |
107 |
compute(r, levelsLeft - 1); |
107 |
} |
108 |
} |
108 |
} |
109 |
} |
109 |
|
|
|
110 |
// update UI, check for stop |
111 |
if (topLevel) |
112 |
{ |
113 |
progressListener.worked(1); |
114 |
if (progressListener.isCanceled()) |
115 |
{ return; } |
116 |
} |
117 |
} |
110 |
} |
118 |
} |
111 |
} |
119 |
} |
112 |
} |
Lines 135-151
public class ObjectMarker
Link Here
|
135 |
|
128 |
|
136 |
public void markMultiThreaded(int threads) throws InterruptedException |
129 |
public void markMultiThreaded(int threads) throws InterruptedException |
137 |
{ |
130 |
{ |
138 |
// to control number of threads, and cleanly wait for comlpetion, create our own pool |
131 |
progressListener.beginTask(Messages.ObjectMarker_MarkingObjects, roots.length); |
139 |
// in theory this should automatically determined by FJ commonPool, however that |
132 |
|
140 |
// would break the interface specifying 'threads' |
|
|
141 |
ForkJoinPool pool = new ForkJoinPool(threads); |
133 |
ForkJoinPool pool = new ForkJoinPool(threads); |
142 |
pool.execute(new FjObjectMarker(roots, bits, outbound, true)); |
134 |
for (int r : roots) { |
|
|
135 |
pool.execute(new FjObjectMarker(r, bits, true)); |
136 |
} |
143 |
pool.shutdown(); |
137 |
pool.shutdown(); |
144 |
while (!pool.awaitTermination(1000, TimeUnit.MILLISECONDS)) |
138 |
while (!pool.awaitTermination(1000, TimeUnit.MILLISECONDS)) |
145 |
{ |
139 |
{ |
146 |
// being stuck here would be a bug; tasks are not ending |
140 |
// wait until completion |
147 |
// TODO is there a heuristic that can be used to flag if no progress is made? |
|
|
148 |
} |
141 |
} |
|
|
142 |
|
143 |
progressListener.done(); |
149 |
} |
144 |
} |
150 |
|
145 |
|
151 |
int countMarked() |
146 |
int countMarked() |