Skip to content

Commit 149da2b

Browse files
author
mgricken
committed
DrJava now deletes the *.java files that the language level
conversion would generate from the *.dj? files. Additionally, it deletes the class files that would be generated. We can actually delete all class files since the language level converter parses the source files and thus knows what top level classes exist. Also removed two log files that had been left in accidentally. M src/edu/rice/cs/drjava/model/compiler/DefaultCompilerModel.java M src/edu/rice/cs/drjava/project/ProjectProfile.java M src/edu/rice/cs/drjava/ui/ProjectPropertiesFrame.java git-svn-id: file:///tmp/test-svn/trunk@4787 fe72c1cf-3628-48e9-8b72-1c46755d3cff
1 parent 2df0898 commit 149da2b

File tree

3 files changed

+74
-31
lines changed

3 files changed

+74
-31
lines changed

drjava/src/edu/rice/cs/drjava/model/compiler/DefaultCompilerModel.java

Lines changed: 74 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -39,13 +39,7 @@
3939
import java.io.File;
4040
import java.io.IOException;
4141

42-
import java.util.List;
43-
import java.util.ArrayList;
44-
import java.util.Arrays;
45-
import java.util.Collections;
46-
import java.util.HashSet;
47-
import java.util.LinkedList;
48-
import java.util.Iterator;
42+
import java.util.*;
4943

5044
import edu.rice.cs.drjava.model.DJError;
5145
import edu.rice.cs.drjava.model.GlobalModel;
@@ -331,20 +325,12 @@ private void _compileFiles(List<? extends File> files, File buildDir) throws IOE
331325
}
332326
}
333327

334-
335328
/** Compiles the language levels files in the list. Adds any errors to the given error list.
336329
* @return An updated list for compilation containing no Language Levels files, or @code{null}
337330
* if there were no Language Levels files to process.
338331
*/
339332
private List<? extends File> _compileLanguageLevelsFiles(List<? extends File> files, List<DJError> errors,
340333
Iterable<File> classPath, Iterable<File> bootClassPath) {
341-
LanguageLevelConverter llc = new LanguageLevelConverter();
342-
Options llOpts;
343-
if (bootClassPath == null) { llOpts = new Options(getActiveCompiler().version(), classPath); }
344-
else { llOpts = new Options(getActiveCompiler().version(), classPath, bootClassPath); }
345-
Pair<LinkedList<JExprParseException>, LinkedList<Pair<String, JExpressionIF>>> llErrors =
346-
llc.convert(files.toArray(new File[0]), llOpts);
347-
348334
/* Rename any .dj0 files in files to be .java files, so the correct thing is compiled. The hashset is used to
349335
* make sure we never send in duplicate files. This can happen if the java file was sent in along with the
350336
* corresponding .dj* file. The dj* file is renamed to a .java file and thus we have two of the same file in
@@ -358,10 +344,82 @@ private List<? extends File> _compileLanguageLevelsFiles(List<? extends File> fi
358344
int lastIndex = fileName.lastIndexOf(".dj");
359345
if (lastIndex != -1) {
360346
containsLanguageLevels = true;
361-
javaFileSet.add(new File(fileName.substring(0, lastIndex) + ".java"));
347+
File javaFile = new File( fileName.substring(0, lastIndex) + ".java");
348+
javaFileSet.add(javaFile);
349+
350+
// Delete the .java file, it will be regenerated later
351+
javaFile.delete();
362352
}
363353
else { javaFileSet.add(canonicalFile); }
364354
}
355+
356+
LanguageLevelConverter llc = new LanguageLevelConverter();
357+
Options llOpts;
358+
if (bootClassPath == null) { llOpts = new Options(getActiveCompiler().version(), classPath); }
359+
else { llOpts = new Options(getActiveCompiler().version(), classPath, bootClassPath); }
360+
Map<File,Set<String>> sourceToTopLevelClassMap = new HashMap<File,Set<String>>();
361+
Pair<LinkedList<JExprParseException>, LinkedList<Pair<String, JExpressionIF>>> llErrors =
362+
llc.convert(files.toArray(new File[0]), llOpts, sourceToTopLevelClassMap);
363+
364+
if (containsLanguageLevels) {
365+
final File buildDir = _model.getBuildDirectory();
366+
final File sourceDir = _model.getProjectRoot();
367+
// System.out.println("Build dir : "+buildDir);
368+
// System.out.println("Source root: "+sourceDir);
369+
// Delete the .class files that match the following pattern:
370+
// XXX.dj? --> XXX.class
371+
// XXX$*.class
372+
// Accessing the disk is the most costly part; therefore, we want to scan each directory only once.
373+
// We create a map from parent directory to class names in that directory.
374+
// Then we scan the files in each directory and delete files that match the class names listed for it.
375+
// dirToClassNameMap: key=parent directory, value=set of classes in this directory
376+
Map<File,Set<String>> dirToClassNameMap = new HashMap<File,Set<String>>();
377+
for(Map.Entry<File,Set<String>> e: sourceToTopLevelClassMap.entrySet()) {
378+
try {
379+
File dir = e.getKey().getParentFile();
380+
if ((buildDir!=null)&&(buildDir!=FileOps.NULL_FILE)&&
381+
(sourceDir!=null)&&(sourceDir!=FileOps.NULL_FILE)) {
382+
// build directory set
383+
String rel = edu.rice.cs.util.FileOps.stringMakeRelativeTo(dir,sourceDir);
384+
dir = new File(buildDir,rel);
385+
}
386+
Set<String> classNames = dirToClassNameMap.get(dir);
387+
if (classNames==null) classNames = new HashSet<String>();
388+
classNames.addAll(e.getValue());
389+
dirToClassNameMap.put(dir,classNames);
390+
// System.out.println(e.getKey()+" --> "+dir);
391+
// for(String name: e.getValue()) {
392+
// System.out.println("\t"+name);
393+
// }
394+
}
395+
catch(IOException ioe) { /* we'll fail to delete this, but that's better than deleting something we shouldn't */ }
396+
}
397+
// Now that we have a map from parent directories to the class names that should be deleted
398+
// in them, we scan the files in each directory, then check if the names match the class names.
399+
for(final Map.Entry<File,Set<String>> e: dirToClassNameMap.entrySet()) {
400+
// System.out.println("Processing dir: "+e.getKey());
401+
// System.out.println("\t"+java.util.Arrays.toString(e.getValue().toArray(new String[0])));
402+
e.getKey().listFiles(new java.io.FilenameFilter() {
403+
public boolean accept(File dir, String name) {
404+
// System.out.println("\t"+name);
405+
int endPos = name.lastIndexOf(".class");
406+
if (endPos<0) return false; // can't be a class file
407+
int dollarPos = name.indexOf('$');
408+
if ((dollarPos>=0) && (dollarPos<endPos)) endPos = dollarPos;
409+
// class name goes to the .class or the first $, whichever comes first
410+
Set<String> classNames = e.getValue();
411+
if (classNames.contains(name.substring(0,endPos))) {
412+
// this is a class file that is generated from a .dj? file
413+
new File(dir,name).delete();
414+
// don't need to return true, we're deleting the file here already
415+
// System.out.println("\t\tDeleted");
416+
}
417+
return false;
418+
}
419+
});
420+
}
421+
}
422+
365423
files = new LinkedList<File>(javaFileSet);
366424

367425
errors.addAll(_parseExceptions2CompilerErrors(llErrors.getFirst()));

drjava/src/edu/rice/cs/drjava/project/ProjectProfile.java

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -142,8 +142,6 @@ public ProjectProfile(File f) throws IOException {
142142
/** @return the name of the file that holds the Jar main class associated with this project */
143143
public String getMainClass() { return _mainClass; }
144144

145-
private static edu.rice.cs.util.Log _LOG = new edu.rice.cs.util.Log("getMainClassContainingFile.txt", true);
146-
147145
/** @return the file containing the project's main class. */
148146
public File getMainClassContainingFile(){
149147
DocFile[] possibleContainers = getSourceFiles();
@@ -154,24 +152,18 @@ public File getMainClassContainingFile(){
154152
main = main.replace(File.separatorChar,'.');
155153
}
156154

157-
_LOG.log("matching against: "+getMainClass());
158-
159155
for(int i = 0; i < possibleContainers.length; i++){
160156
String toMatch = possibleContainers[i].getAbsolutePath();
161157
toMatch = toMatch.substring(0, toMatch.lastIndexOf(".java"));
162158
toMatch = toMatch.replace(File.separatorChar,'.');
163159

164-
_LOG.log("\t"+toMatch);
165-
166160
if(toMatch.endsWith(main))
167161
return possibleContainers[i];
168162
}
169163

170164
//Return a guess at the main class if its not in a source file
171165
File toRet = new File(main.replace('.',File.separatorChar)+".java");
172166

173-
_LOG.log("\t"+toRet.getAbsolutePath());
174-
175167
return toRet;
176168
}
177169

drjava/src/edu/rice/cs/drjava/ui/ProjectPropertiesFrame.java

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -218,8 +218,6 @@ private void reset(File projRoot) {
218218
_applyButton.setEnabled(false);
219219
}
220220

221-
static edu.rice.cs.util.Log Log = new edu.rice.cs.util.Log("saveSettings.txt", true);
222-
223221
/** Caches the settings in the global model */
224222
public boolean saveSettings() {//throws IOException {
225223
boolean projRootChanged = false;
@@ -241,11 +239,8 @@ public boolean saveSettings() {//throws IOException {
241239
_model.setWorkingDirectory(wd);
242240

243241
String mc = _mainDocumentSelector.getText();
244-
Log.log("set: "+mc+"\n");
245242
if(mc == null) mc = "";
246243
_model.setMainClass(mc);
247-
Log.log("get: "+_model.getMainClass());
248-
Log.log("file: "+_model.getMainClassContainingFile());
249244

250245
Vector<File> extras = _extraClassPathList.getValue(); // Vector mandated by interface to VectorFileOptionComponent
251246
_model.setExtraClassPath(IterUtil.snapshot(extras));
@@ -261,8 +256,6 @@ public boolean saveSettings() {//throws IOException {
261256
} catch(IOException e) { throw new edu.rice.cs.util.UnexpectedException(e, "I/O error while reloading project"); }
262257
}
263258

264-
Log.log("post: "+_mainDocumentSelector.getText());
265-
266259
return true;
267260
}
268261

0 commit comments

Comments
 (0)