Community
Participate
Working Groups
Build: Release 3.0.0 Jerome reported slowness while opening a Java Editor on Parser.java in JDT Core. Although he reported against 3.1 M1, I did some profiling with the 3.0.0 release. Using a native profiler, I found a lot of time (15%) was spent in the garbage collector. In a Java profiler, I then took a look at the big sources of object creations. In total, over 800,000 garbage objects (>60 MB) are created when opening this editor once. This is mostly Object[] (212,000 instances), StyleRange (160,000 instances), char[] (117,069), and Region (97,000 instances). One example I found that might be easy to improve: 272 instances of jdt.internal.core.util.PublicScanner are created (see first attachment for backtraces). This in turn creates 51,238 Object[] objects. If a single parser could somehow be reused, rather than creating many parser instances, it would save many object creations. Steps: 1. Start Eclipse. 2. Accept path to workspace 3. Close Welcome view 4. Window > Open Perspective > Java 5. File > Import External Plug-ins and Fragments > Next > 6. Project with source folders > Next > 7. Select org.eclipse.jdt.core > Add > Finish 8. Navigate > Open Type... > Type in 'Parser' > Select the class (C) Parser > Qualifier: org.eclipse.jdt.internal.compiler.parser > OK 9. Close the editor 10. Repeat step 8 (all classes are now loaded)
Created attachment 14434 [details] Allocation backtraces for PublicScanner
Is this regression consistent across different VMs? For example the impact of bug 63681, bug 63718 and Folding scales with the size of the CU.
We also observed that editing feels slower. Needs to be investigated
I only did the profiling on one build (3.0.0), so I can't comment on any regression. The profiler measurements were taken with Sun 1.4.2-b28 VM.
I did some profiling of this scenario in relation to a J9 bug I am tracking, but I thought the results would be interesting here. All results are from opening and then closing Parser.java in the Java perspective. I have a simple plugin that starts a timer, opens and closes the editor, then stops the timer. I always discarded the first ten runs (proportionally similar results, but slower), and then timed the average of 40 runs. The first four are with out-of-box preference settings. I am using the most recent IBM JRE (20040908). Here are the results: Build M20040908: 1.11 seconds Build 3.1 M1: 1.35 seconds Build 3.1 M1, code folding and quick diff disabled: 0.85 seconds So, roughly 20% regression in time to open the editor. Code folding and quick diff add a 60% hit.
John, just to be sure, M20040908 does not show a regression? It is 3.1M1 that shows it?
re comments 3: Is was comparing 3.1 builds with R3.0. I do not see such a regression when using 3.0.1 builds. A typing areas which is slower in 3.1 builds is for example the Ctrl+Click feature. I filed a new bug 73589 to investigate this.
My initial profiler information is for the 3.0.0 release build. The measurements I did later were strictly on M20040908 and 3.1 M1. I did not produce performance numbers comparing 3.0.0 to any other build. The short summary is: this scenario creates a lot of garbage in 3.0.0, and is slower in 3.1 M1 than in 3.0.1.
We measured the performance of opening a text and Java editor and can confirm the regression for the Java editor from 3.0 to 3.1 but not from 3.0 to 3.0.1.
Jerome, would there be less object creations (not counting the scanners ;-) if we reuse the scanner and call setSource instead of creating a scanner each time?
Yes, much less objects would be created. However we just discovered that the public scanner cannot be reused with different sources (see bug 73762). Do you call setSource(...) with different sources (when opening one editor) ? I guess not ...
You guess wrong: if we change to reuse the parser we would set different sources (the source of an individual Java element).
Trying to guess again :-) All Java elements are in the same CU and for each Java element you use setSource(...) passing the source obtained using ISourceReference#getSource() ? If this is true, you should set the source of the whole CU, and use resetTo(...) with the positions of each Java element obtained using ISourceReference#getSourceRange(). Of course the line ends would be relative to the whole CU, but that would be even easier to map in the Java editor, right ?
We have a working copy not a CU. The code changes while editing. As a result we need to parse the changed java elements. We would still need to create a new parser for each java element delta if setSource does not work, right?
That's correct.
In today's build, bug 73762 is fixed so the public scanner can be reused with different sources.
The regression in the 3.1 stream seems to be gone in latest builds (changes in J Core I assume), e.g. I200409210010. The open Java editor performance test results are in the R3.0 range again. Also, bug 73589 seems fixed. Adapting summary and severity.
Adding my name to the cc list as we are now tracking performance issues more closely. Please remove the performance keyword if this is not a performance bug.
Are there still outstanding work items here? From the comments above, it sounds like this could be closed.
Nothing has been done yet. What made you think that this got fixed?
"regression in the 3.1 stream seems to be gone"
Deferred.
Resetting priority to P3. Will be reassessed for the next release.
Fixed in HEAD. Available in builds > N20061111-0010.
Created attachment 53687 [details] Performance Results The attached performance tests of opening the Java editor shows a performance gain up to 10% depending on the use case. As expected testOpenEditor4 and testOpenEditor6 show no improvement as folding is disabled there. The biggest performance gains comes with enabled folding and especially with large files (testOpenEditor3 and testOpenEditor5). Of course the fix also improves the performance of updating the folding structure while typing (during reconcile).