I could immediately recreate this problem on the MacBook.
YourKit shows that along the call tree below, over the course of about a minute of running in this state, about 21 million calls to File.equals and 14 million calls to String.indexOf were made from CompilerErrorModel._calculatePositions, which was only called once itself. So that's where I suspect the problem.
The problem is indeed in _calculatePositions(). While I haven't figured out the reason yet, I've determined using logging that in the following piece of code, the inner while loop is NEVER entered, yet it contains the only statement that advances curError (starting at approximately line 329):
// offset is always pointing to the first character in the line
// containing an error (or the last line of the previous file) at the top of this loop
while ((curError < _numErrors) && // we still have errors to find
file.equals(_errors[curError].file()) && // the next error is in this file
(offset <= defsLength)) { // we haven't gone past the end of the file
POSLOG.log("in _calculatePositions, in while loop 3");
// create new positions for all errors on this line
while ((curError < _numErrors) && file.equals(_errors[curError].file()) && // we are still in this file
(_errors[curError].lineNumber() == curLine)) {
_positions[curError] = document.createPosition(offset + _errors[curError].startColumn());
curError++;
POSLOG.log("in _calculatePositions, in while loop 4");
}
While loop 4 is never even entered, so curError++ is not executed, and while loop 3 never ends. I'll now examine the conditions involved in the loop.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
The inner while loop is never entered because the line numbers don't match. This seems to be the cause of a DOS/Unix line feed incompatibility (javac is reporting a line number that is out of range for the actual document). I don't quite know what to do about this, but I think I can manage to just NOT report a line number. That will fix the infinite loop, which was the result of a corner case that someone didn't think about.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
As of revision 4212, this problem has been fixed.
I chose to leave the incorrect line number information in the error; it is perhaps confusing, but it is more informative than reporting "no line number associated" and also hints at the line ending problem.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Project that causes 100% CPU use
Logged In: YES
user_id=1075744
Originator: NO
I could immediately recreate this problem on the MacBook.
YourKit shows that along the call tree below, over the course of about a minute of running in this state, about 21 million calls to File.equals and 14 million calls to String.indexOf were made from CompilerErrorModel._calculatePositions, which was only called once itself. So that's where I suspect the problem.
Here's the call tree:
edu.rice.cs.drjava.model.compiler.CompilerErrorModel._calculatePositions()
edu.rice.cs.drjava.model.compiler.CompilerErrorModel.<init>(CompilerError[], GlobalModel)
edu.rice.cs.drjava.model.compiler.DefaultCompilerModel._distributeErrors(List)
edu.rice.cs.drjava.model.compiler.DefaultCompilerModel._compileFiles(List, File)
edu.rice.cs.drjava.model.compiler.DefaultCompilerModel._doCompile(List)
edu.rice.cs.drjava.model.compiler.DefaultCompilerModel.compileProject()
edu.rice.cs.drjava.ui.MainFrame._compileProject()
edu.rice.cs.drjava.ui.MainFrame.access$4100(MainFrame)
edu.rice.cs.drjava.ui.MainFrame$44.actionPerformed(ActionEvent)
Hope this helps.
Logged In: YES
user_id=1075744
Originator: NO
The problem is indeed in _calculatePositions(). While I haven't figured out the reason yet, I've determined using logging that in the following piece of code, the inner while loop is NEVER entered, yet it contains the only statement that advances curError (starting at approximately line 329):
// offset is always pointing to the first character in the line
// containing an error (or the last line of the previous file) at the top of this loop
while ((curError < _numErrors) && // we still have errors to find
file.equals(_errors[curError].file()) && // the next error is in this file
(offset <= defsLength)) { // we haven't gone past the end of the file
POSLOG.log("in _calculatePositions, in while loop 3");
// create new positions for all errors on this line
while ((curError < _numErrors) && file.equals(_errors[curError].file()) && // we are still in this file
(_errors[curError].lineNumber() == curLine)) {
_positions[curError] = document.createPosition(offset + _errors[curError].startColumn());
curError++;
POSLOG.log("in _calculatePositions, in while loop 4");
}
While loop 4 is never even entered, so curError++ is not executed, and while loop 3 never ends. I'll now examine the conditions involved in the loop.
Logged In: YES
user_id=1075744
Originator: NO
The inner while loop is never entered because the line numbers don't match. This seems to be the cause of a DOS/Unix line feed incompatibility (javac is reporting a line number that is out of range for the actual document). I don't quite know what to do about this, but I think I can manage to just NOT report a line number. That will fix the infinite loop, which was the result of a corner case that someone didn't think about.
Logged In: YES
user_id=1075744
Originator: NO
As of revision 4212, this problem has been fixed.
I chose to leave the incorrect line number information in the error; it is perhaps confusing, but it is more informative than reporting "no line number associated" and also hints at the line ending problem.