1 /*
2  * Copyright (C) 2007 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package org.apache.harmony.tests.java.lang;
18 
19 import android.platform.test.annotations.LargeTest;
20 
21 import junit.framework.TestCase;
22 
23 import java.io.BufferedReader;
24 import java.io.File;
25 import java.io.FileOutputStream;
26 import java.io.IOException;
27 import java.io.InputStream;
28 import java.io.InputStreamReader;
29 import java.io.OutputStream;
30 import java.nio.file.Files;
31 import java.nio.file.Path;
32 
33 public class ProcessManagerTest extends TestCase {
34 
35     Thread thread = null;
36     Process process = null;
37     boolean isThrown = false;
38     private static final Path TEMP_DIR;
39 
40     static {
41         try {
42             TEMP_DIR = Files.createTempDirectory("process-manager-test");
43             TEMP_DIR.toFile().deleteOnExit();
44         } catch (IOException e) {
45             throw new RuntimeException(e);
46         }
47     }
48 
testCat()49     public void testCat() throws IOException, InterruptedException {
50         String[] commands = { "cat" };
51         Process process = Runtime.getRuntime().exec(commands, null, null);
52 
53         OutputStream out = process.getOutputStream();
54         String greeting = "Hello, World!";
55         out.write(greeting.getBytes());
56         out.write('\n');
57         out.close();
58 
59         assertEquals(greeting, readLine(process));
60     }
61 
62     // BrokenTest: Sporadic failures in CTS, but not in CoreTestRunner
testSleep()63     public void testSleep() throws IOException {
64         String[] commands = { "sleep", "1" };
65         process = Runtime.getRuntime().exec(commands, null, null);
66         try {
67             assertEquals(0, process.waitFor());
68 
69         } catch(InterruptedException ie) {
70             fail("InterruptedException was thrown.");
71         }
72 
73         isThrown = false;
74         thread = new Thread() {
75             public void run() {
76                 String[] commands = { "sleep", "1000"};
77                 try {
78                     process = Runtime.getRuntime().exec(commands, null, null);
79                 } catch (IOException e1) {
80                     fail("IOException was thrown.");
81                 }
82                 try {
83                     process.waitFor();
84                     fail("InterruptedException was not thrown.");
85                 } catch(InterruptedException ie) {
86                     isThrown = true;
87                 }
88             }
89         };
90 
91         Thread interruptThread = new Thread() {
92             public void run() {
93                 try {
94                     sleep(10);
95                 } catch(InterruptedException ie) {
96                     fail("InterruptedException was thrown in " +
97                             "the interruptThread.");
98                 }
99                 thread.interrupt();
100             }
101         };
102         thread.start();
103         interruptThread.start();
104         try {
105             interruptThread.join();
106         } catch (InterruptedException e) {
107             fail("InterruptedException was thrown.");
108         }
109         try {
110             Thread.sleep(100);
111         } catch(InterruptedException ie) {
112 
113         }
114 
115         thread.interrupt();
116         try {
117             Thread.sleep(100);
118         } catch(InterruptedException ie) {
119 
120         }
121 
122         assertTrue(isThrown);
123         // Destroy process, otherwise it will run until 1000 seconds
124         // have elapsed but we don't need it again for this test.
125         process.destroy();
126     }
127 
testPwd()128     public void testPwd() throws IOException, InterruptedException {
129         String[] commands = { "sh", "-c", "pwd" };
130         Process process = Runtime.getRuntime().exec(
131                 commands, null, new File("/"));
132         logErrors(process);
133         assertEquals("/", readLine(process));
134     }
135 
testEnvironment()136     public void testEnvironment() throws IOException, InterruptedException {
137         String[] commands = { "sh", "-c", "echo $FOO" };
138 
139         // Remember to set the path so we can find sh.
140         String[] environment = { "FOO=foo", "PATH=" + System.getenv("PATH") };
141         Process process = Runtime.getRuntime().exec(
142                 commands, environment, null);
143         logErrors(process);
144         assertEquals("foo", readLine(process));
145     }
146 
readLine(Process process)147     String readLine(Process process) throws IOException {
148         InputStream in = process.getInputStream();
149         BufferedReader reader = new BufferedReader(new InputStreamReader(in));
150         return reader.readLine();
151     }
152 
logErrors(final Process process)153     void logErrors(final Process process) throws IOException {
154         Thread thread = new Thread() {
155             public void run() {
156                 InputStream in = process.getErrorStream();
157                 BufferedReader reader
158                         = new BufferedReader(new InputStreamReader(in));
159                 String line;
160                 try {
161                     while ((line = reader.readLine()) != null) {
162                         System.err.println(line);
163                     }
164                 } catch (IOException e) {
165                     e.printStackTrace();
166                 }
167             }
168         };
169         thread.setDaemon(true);
170         thread.start();
171     }
172 
173     @LargeTest
testHeavyLoad()174     public void testHeavyLoad() {
175         int i;
176         for (i = 0; i < 30; i++)
177             stuff();
178     }
179 
stuff()180     private static void stuff() {
181         Runtime rt = Runtime.getRuntime();
182         try {
183             Process proc = rt.exec("ls " + TEMP_DIR.toString());
184             proc.waitFor();
185         } catch (Exception ex) {
186             System.err.println("Failure: " + ex);
187             throw new RuntimeException(ex);
188         }
189     }
190 
191     FileOutputStream out;
192 
testCloseNonStandardFds()193     public void testCloseNonStandardFds()
194             throws IOException, InterruptedException {
195         String[] commands = { "ls", "/proc/self/fd" };
196 
197         Process process = Runtime.getRuntime().exec(commands, null, null);
198         int before = countLines(process);
199 
200         File tmpFile = File.createTempFile("testCloseNonStandardFds", ".txt");
201         // Open a new fd.
202         this.out = new FileOutputStream(tmpFile);
203 
204         try {
205             process = Runtime.getRuntime().exec(commands, null, null);
206             int after = countLines(process);
207 
208             // Assert that the new fd wasn't open in the second run.
209             assertEquals(before, after);
210         } finally {
211             this.out.close();
212             tmpFile.delete();
213         }
214     }
215 
216     /**
217      * Counts lines of input from the given process. Equivalent to "wc -l".
218      */
countLines(Process process)219     private int countLines(Process process) throws IOException {
220         logErrors(process);
221         InputStream in = process.getInputStream();
222         BufferedReader reader = new BufferedReader(new InputStreamReader(in));
223         int count = 0;
224         while (reader.readLine() != null) {
225             count++;
226         }
227         return count;
228     }
229 
testInvalidCommand()230     public void testInvalidCommand()
231             throws IOException, InterruptedException {
232         try {
233             String[] commands = { "doesnotexist" };
234             Runtime.getRuntime().exec(commands, null, null);
235         } catch (IOException e) { /* expected */ }
236     }
237 }
238