Spoofax completion through API seems to reload entire language on every completion
Using Spoofax release 2.1.0.
After loading my Spoofax language, parsing a program takes around 5 milliseconds.
However, completing a program takes orders of magnitude longer: around 500 milliseconds if the program has no syntactic errors, and, in between 1 to 2 seconds if the program does has syntactic errors.
I doubt this overhead comes from the Stratego transformations that are needed for completion. More likely, it’s doing something heavy like reloading my language (this is just a suspicion).
All the time is spend in the following call:Submitted by Oskar van Rest on 14 August 2017 at 01:39
spoofax.completionService.get(cursor, parseResult, false);
I had a look at JSGLRCompletionService.java. At least one problem seems to be the new JSGLRParseConfiguration that gets created.
The following code executes in ~5 ms:
final JSGLRParserConfiguration config = null; final ISpoofaxInputUnit input = parseResult.input(); final ISpoofaxInputUnit modifiedInput = unitService.inputUnit(input.source(), input.text(), input.langImpl(), input.dialect(), config); ISpoofaxParseUnit completionParseResult = syntaxService.parse(modifiedInput);
However, the following code (lines 90-95 in JSGLRCompletionService.java) takes around 500 ms to execute:
final JSGLRParserConfiguration config = new JSGLRParserConfiguration(true, true, true, 3000, cursor); final ISpoofaxInputUnit input = parseResult.input(); final ISpoofaxInputUnit modifiedInput = unitService.inputUnit(input.source(), input.text(), input.langImpl(), input.dialect(), config); ISpoofaxParseUnit completionParseResult = syntaxService.parse(modifiedInput);
Note: the fragments are the same except for the first lines.
Not sure if this is the only thing that takes long.
The first line puts the parser in “completion” mode, where it uses “empty” rules to insert symbols (insertion rules) and predict the proposals.
We haven’t measured the overhead of this operation, but I would assume it is very expensive. The approach is based on the strategy for error recovery, but it calculates all possible recoveries, applying insertion rules at the cursor position and creating ambiguity nodes.
On the other hand, for programs without syntax errors, parsing should not take this long, as it is not necessary to try these insertion rules. I will check the code, to guarantee that the parser does not enter the completion mode when it is not necessary.
Log in to post comments