KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > armedbear > j > CompilationBuffer


1 /*
2  * CompilationBuffer.java
3  *
4  * Copyright (C) 1998-2004 Peter Graves
5  * $Id: CompilationBuffer.java,v 1.18 2004/05/21 22:44:44 piso Exp $
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20  */

21
22 package org.armedbear.j;
23
24 import java.io.BufferedReader JavaDoc;
25 import java.io.IOException JavaDoc;
26 import java.io.InputStream JavaDoc;
27 import java.io.InputStreamReader JavaDoc;
28 import java.util.ArrayList JavaDoc;
29 import javax.swing.SwingUtilities JavaDoc;
30
31 public final class CompilationBuffer extends CompilationErrorBuffer
32     implements Runnable JavaDoc
33 {
34     private String JavaDoc command;
35     private String JavaDoc expandedCommand;
36     private Position posEndOfBuffer;
37     private File currentDir;
38     private Process JavaDoc process;
39     private int exitValue;
40     private File exitValueFile;
41
42     public CompilationBuffer(String JavaDoc command, File directory)
43     {
44         setCommand(command);
45         currentDir = directory;
46         mode = CompilationMode.getMode();
47         try {
48             lockWrite();
49         }
50         catch (InterruptedException JavaDoc e) {
51             Log.debug(e);
52             return;
53         }
54         try {
55             appendLine("");
56             renumber();
57         }
58         finally {
59             unlockWrite();
60         }
61         setLoaded(true);
62         posEndOfBuffer = new Position(getFirstLine(), 0);
63     }
64
65     public synchronized final void initialize()
66     {
67         setTitle(expandedCommand = expandCommand(command));
68         setInitialized(true);
69     }
70
71     public final void setCommand(String JavaDoc command)
72     {
73         this.command = command;
74     }
75
76     public final int exitValue()
77     {
78         return exitValue;
79     }
80
81     public void empty()
82     {
83         try {
84             lockWrite();
85         }
86         catch (InterruptedException JavaDoc e) {
87             Log.debug(e);
88             return;
89         }
90         try {
91             super.empty();
92             appendLine("");
93             renumber();
94             setLoaded(true);
95             posEndOfBuffer = new Position(getFirstLine(), 0);
96             setCurrentError(null);
97         }
98         finally {
99             unlockWrite();
100         }
101         for (EditorIterator it = new EditorIterator(); it.hasNext();) {
102             Editor ed = it.nextEditor();
103             if (ed.getBuffer() == this) {
104                 ed.setDot(getFirstLine(), 0);
105                 ed.setTopLine(getFirstLine());
106                 ed.setMark(null);
107             }
108         }
109     }
110
111     public void run()
112     {
113         long start = System.currentTimeMillis();
114         if (expandedCommand.startsWith("(")) {
115             // Lisp.
116
FastStringBuffer sb = new FastStringBuffer();
117             sb.append("(with-output-to-string (s) ");
118             sb.append("(let ((*standard-output* s)) ");
119             sb.append(expandedCommand);
120             sb.append(" ))");
121             try {
122                 org.armedbear.lisp.LispObject result =
123                     JLisp.runLispCommand(sb.toString());
124                 appendLater(result.getStringValue());
125             }
126             catch (Throwable JavaDoc t) {
127                 Log.debug(t);
128             }
129         } else {
130             startProcess();
131             if (process != null) {
132                 CompilationBufferReaderThread stdoutThread =
133                     new CompilationBufferReaderThread(process.getInputStream());
134                 stdoutThread.start();
135                 CompilationBufferReaderThread stderrThread =
136                     new CompilationBufferReaderThread(process.getErrorStream());
137                 stderrThread.start();
138                 try {
139                     exitValue = process.waitFor();
140                     if (exitValueFile != null && exitValueFile.isFile()) {
141                         exitValue = getExitValueFromFile(exitValueFile);
142                         exitValueFile.delete();
143                         exitValueFile = null;
144                     }
145                     stdoutThread.join();
146                     stderrThread.join();
147                     long elapsed = System.currentTimeMillis() - start;
148                     FastStringBuffer sb = new FastStringBuffer();
149                     sb.append("\nCompilation ");
150                     if (exitValue == 0) {
151                         sb.append("finished (");
152                         sb.append(String.valueOf(elapsed));
153                         sb.append(" milliseconds)");
154                     } else
155                         sb.append("exited abnormally");
156                     sb.append("\n");
157                     appendLater(sb.toString());
158                 }
159                 catch (InterruptedException JavaDoc e) {
160                     Log.error(e);
161                 }
162             } else
163                 appendLater("Unable to start compilation process\n");
164         }
165         Editor.getTagFileManager().setEnabled(true);
166     }
167
168     private void startProcess()
169     {
170         process = null;
171         exitValue = -1;
172         try {
173             if (Platform.isPlatformWindows()) {
174                 String JavaDoc cmd = "cd /d \"" + currentDir.canonicalPath() +
175                     "\" && " + expandedCommand;
176                 ArrayList JavaDoc list = new ArrayList JavaDoc();
177                 list.add("cmd.exe");
178                 list.add("/c");
179                 list.addAll(Utilities.tokenize(cmd));
180                 final int size = list.size();
181                 String JavaDoc[] cmdarray = new String JavaDoc[size];
182                 for (int i = 0; i < size; i++)
183                     cmdarray[i] = (String JavaDoc) list.get(i);
184                 process = Runtime.getRuntime().exec(cmdarray);
185             } else {
186                 // Not Windows. Assume Unix.
187
if (Utilities.haveJpty()) {
188                     exitValueFile = Utilities.getTempFile();
189                     FastStringBuffer sb = new FastStringBuffer();
190                     sb.append("(\\cd \"");
191                     sb.append(currentDir.canonicalPath());
192                     sb.append("\" && ");
193                     sb.append(expandedCommand);
194                     sb.append("; echo $? > ");
195                     sb.append(exitValueFile.canonicalPath());
196                     sb.append(')');
197                     final String JavaDoc cmd = sb.toString();
198                     String JavaDoc[] cmdarray = {"jpty", "/bin/sh", "-c", cmd};
199                     process = Runtime.getRuntime().exec(cmdarray);
200                 } else {
201                     String JavaDoc cmd = "(\\cd \"" + currentDir.canonicalPath() +
202                         "\" && " + expandedCommand + ")";
203                     String JavaDoc[] cmdarray = {"/bin/sh", "-c", cmd};
204                     process = Runtime.getRuntime().exec(cmdarray);
205                 }
206             }
207         }
208         catch (Throwable JavaDoc t) {
209             Log.error(t);
210         }
211     }
212
213     private String JavaDoc expandCommand(String JavaDoc s)
214     {
215         int length = s.length();
216         FastStringBuffer sb = new FastStringBuffer();
217         boolean inQuote = false;
218         for (int i = 0; i < length; i++) {
219             char c = s.charAt(i);
220             if (inQuote) {
221                 sb.append(c);
222                 if (c == '"')
223                     inQuote = false;
224             } else {
225                 // Not in quote.
226
if (c == '"') {
227                     sb.append(c);
228                     inQuote = true;
229                 } else if (c == 'h') {
230                     boolean replaced = false;
231                     if (s.regionMatches(i, "here", 0, 4)) {
232                         // "here" must be delimited by spaces.
233
if (i == 0 || s.charAt(i-1) == ' ') {
234                             if (i+4 == length || s.charAt(i+4) == ' ') {
235                                 File file = parentBuffer.getFile();
236                                 if (file != null) {
237                                     String JavaDoc cp = file.canonicalPath();
238                                     if (cp.indexOf(' ') >= 0) {
239                                         // Enclose filename in double quotes
240
// since it contains an embedded space.
241
sb.append('"');
242                                         sb.append(cp);
243                                         sb.append('"');
244                                     } else
245                                         sb.append(cp);
246                                     replaced = true;
247                                 }
248                             }
249                         }
250                     }
251                     if (replaced)
252                         i += 3;
253                     else
254                         sb.append(c);
255                 } else
256                     sb.append(c);
257             }
258         }
259         return sb.toString();
260     }
261
262     private int getExitValueFromFile(File file)
263     {
264         int ret = -1;
265         if (file != null) {
266             try {
267                 InputStream JavaDoc inputStream = file.getInputStream();
268                 BufferedReader JavaDoc reader =
269                     new BufferedReader JavaDoc(new InputStreamReader JavaDoc(inputStream));
270                 String JavaDoc s = reader.readLine();
271                 reader.close();
272                 try {
273                     ret = Integer.parseInt(s);
274                 }
275                 catch (NumberFormatException JavaDoc e) {}
276             }
277             catch (IOException JavaDoc e) {}
278         }
279         return ret;
280     }
281
282     public static void killCompilation()
283     {
284         for (BufferIterator it = new BufferIterator(); it.hasNext();) {
285             Buffer buf = it.nextBuffer();
286             if (buf instanceof CompilationBuffer) {
287                 ((CompilationBuffer)buf).killProcess();
288                 break;
289             }
290         }
291     }
292
293     private synchronized void killProcess()
294     {
295         if (process != null) {
296             process.destroy();
297             try {
298                 process.waitFor();
299                 process = null;
300             }
301             catch (InterruptedException JavaDoc e) {
302                 Log.error(e);
303             }
304         }
305     }
306
307     public void dispose()
308     {
309         killProcess();
310     }
311
312     private void appendLater(final String JavaDoc s)
313     {
314         Runnable JavaDoc runnable = new Runnable JavaDoc() {
315             public void run()
316             {
317                 Position pos = posEndOfBuffer;
318                 insertString(pos, s);
319                 if (needsRenumbering())
320                     renumber();
321                 for (EditorIterator it = new EditorIterator(); it.hasNext();) {
322                     Editor ed = it.nextEditor();
323                     if (ed.getBuffer() == CompilationBuffer.this) {
324                         ed.eob();
325                         ed.getDisplay().setReframe(-2);
326                         ed.setUpdateFlag(REPAINT);
327                         ed.updateDisplay();
328                     }
329                 }
330                 resetUndo();
331             }
332         };
333         SwingUtilities.invokeLater(runnable);
334     }
335
336     public String JavaDoc getFileNameForDisplay()
337     {
338         return getTitle();
339     }
340
341     public File getCurrentDirectory()
342     {
343         return currentDir;
344     }
345
346     public void setCurrentDirectory(File directory)
347     {
348         currentDir = directory;
349     }
350
351     // For the buffer list.
352
public String JavaDoc toString()
353     {
354         return command;
355     }
356
357     private class CompilationBufferReaderThread extends ReaderThread
358     {
359         public CompilationBufferReaderThread(InputStream JavaDoc inputStream)
360         {
361             super(inputStream);
362         }
363
364         public void update(final String JavaDoc s)
365         {
366             appendLater(s);
367         }
368     }
369 }
370
Popular Tags