Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/test/hotspot/jtreg/vmTestbase/nsk/share/aod/ProcessExecutor.java
41161 views
1
/*
2
* Copyright (c) 2008, 2018, 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
package nsk.share.aod;
24
25
import java.io.*;
26
import java.util.*;
27
import nsk.share.*;
28
29
public class ProcessExecutor {
30
31
private String[] cmdLine;
32
33
private long timeout;
34
35
private boolean printProcessOutput;
36
37
private String processOutputPrefix;
38
39
private InputStreamReaderThread outReader;
40
41
private InputStreamReaderThread errReader;
42
43
private Process startedProcess;
44
45
private ProcessWaiterThread processWaiter;
46
47
private long expectedFinishTime;
48
49
private volatile boolean executionCompleted;
50
51
private int exitCode;
52
53
private class InputStreamReaderThread extends Thread {
54
private BufferedReader in;
55
56
private String outputPrefix;
57
58
private List<String> output = new ArrayList<String>();
59
60
private volatile boolean streamWasAbruptlyClosed;
61
62
private Throwable unexpectedException;
63
64
public InputStreamReaderThread(InputStream in, String prefix) {
65
this.in = new BufferedReader(new InputStreamReader(in));
66
this.outputPrefix = prefix;
67
setDaemon(true);
68
}
69
70
public void streamWasAbruptlyClosed(boolean newValue) {
71
streamWasAbruptlyClosed = newValue;
72
}
73
74
public void run() {
75
try {
76
while (true) {
77
String line = in.readLine();
78
if (line == null)
79
return;
80
81
output.add(line);
82
83
if (printProcessOutput)
84
System.out.println(outputPrefix + line);
85
}
86
} catch (IOException e) {
87
if (!streamWasAbruptlyClosed) {
88
unexpectedException = e;
89
e.printStackTrace( );
90
}
91
} catch (Throwable t) {
92
unexpectedException = t;
93
t.printStackTrace( );
94
}
95
}
96
97
void checkStatus() {
98
if (unexpectedException != null)
99
throw new Failure("Exception was thrown during InputStreamReaderThread work: " + unexpectedException,
100
unexpectedException);
101
}
102
}
103
104
private class ProcessWaiterThread extends Thread {
105
106
private Throwable unexpectedException;
107
108
private Process process;
109
110
private InputStreamReaderThread outReader;
111
112
private InputStreamReaderThread errReader;
113
114
ProcessWaiterThread(Process process, InputStreamReaderThread outReader, InputStreamReaderThread errReader) {
115
this.process = process;
116
this.outReader = outReader;
117
this.errReader = errReader;
118
119
setDaemon(true);
120
}
121
122
public void run() {
123
try {
124
exitCode = process.waitFor();
125
outReader.join();
126
errReader.join();
127
128
synchronized (ProcessWaiterThread.this) {
129
executionCompleted = true;
130
ProcessWaiterThread.this.notify();
131
}
132
} catch (InterruptedException e) {
133
/*
134
* ProcessWaiterThread is interrupted if started process
135
* didn't finish in expected time
136
*/
137
} catch (Throwable t) {
138
unexpectedException = t;
139
t.printStackTrace();
140
}
141
}
142
143
void checkStatus() {
144
if (unexpectedException != null)
145
throw new Failure("Exception was thrown during ProcessWaiterThread work: "
146
+ unexpectedException, unexpectedException);
147
}
148
}
149
150
public ProcessExecutor(String cmdLine, long timeout) {
151
this.cmdLine = new String[]{cmdLine};
152
this.timeout = timeout;
153
}
154
155
public ProcessExecutor(String cmdLine, long timeout, String outputPrefix) {
156
this(cmdLine, timeout);
157
this.printProcessOutput = true;
158
this.processOutputPrefix = outputPrefix;
159
}
160
161
public void startProcess() throws IOException {
162
if (cmdLine.length == 1)
163
startedProcess = Runtime.getRuntime().exec(cmdLine[0]);
164
else
165
startedProcess = Runtime.getRuntime().exec(cmdLine);
166
167
expectedFinishTime = System.currentTimeMillis() + timeout;
168
169
outReader = new InputStreamReaderThread(startedProcess.getInputStream(),
170
processOutputPrefix == null ? "" : processOutputPrefix + " (stdout): ");
171
errReader = new InputStreamReaderThread(startedProcess.getErrorStream(),
172
processOutputPrefix == null ? "" : processOutputPrefix + " (stderr): ");
173
174
outReader.start();
175
errReader.start();
176
177
processWaiter = new ProcessWaiterThread(startedProcess, outReader, errReader);
178
processWaiter.start();
179
}
180
181
182
public void waitForProcess() throws InterruptedException {
183
synchronized (processWaiter) {
184
while ((System.currentTimeMillis() < expectedFinishTime) && !executionCompleted) {
185
processWaiter.wait(expectedFinishTime - System.currentTimeMillis());
186
}
187
}
188
189
if (!executionCompleted) {
190
destroyProcessAndWaitThreads();
191
192
executionCompleted = true;
193
194
throw new Failure("Execution timed out (timeout: " + timeout + "ms)");
195
}
196
}
197
198
private void destroyProcessAndWaitThreads() {
199
outReader.streamWasAbruptlyClosed(true);
200
errReader.streamWasAbruptlyClosed(true);
201
202
processWaiter.interrupt();
203
startedProcess.destroy();
204
205
try {
206
outReader.join();
207
errReader.join();
208
processWaiter.join();
209
210
outReader.checkStatus();
211
errReader.checkStatus();
212
processWaiter.checkStatus();
213
} catch (InterruptedException e) {
214
throw new Failure("Unexpected InterruptedException", e);
215
}
216
}
217
218
private void checkProcessState() {
219
if (!executionCompleted)
220
throw new IllegalStateException("Process didn't finish execution");
221
}
222
223
public void destroyProcess() {
224
if (executionCompleted)
225
return;
226
227
destroyProcessAndWaitThreads();
228
}
229
230
public long pid() {
231
return startedProcess.pid();
232
}
233
234
public int getExitCode() {
235
checkProcessState();
236
237
return exitCode;
238
}
239
240
public List<String> getProcessOut() {
241
checkProcessState();
242
243
return outReader.output;
244
}
245
246
public List<String> getProcessErr() {
247
checkProcessState();
248
249
return errReader.output;
250
}
251
}
252
253