Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix race condition in LanguageServerWrapper resulting in NullPointerException during LS initialization #985

Merged
merged 3 commits into from
May 8, 2024

Conversation

sebthom
Copy link
Member

@sebthom sebthom commented May 3, 2024

When running the test suite on Windows and in Docker with Ubuntu, a lot of NPEs with the following stacktrace are thrown:

java.lang.NullPointerException: Cannot invoke
"org.eclipse.core.runtime.IProgressMonitor.done()" because
"this.this$0.initializeFutureMonitor" is null
	at org.eclipse.lsp4e.LanguageServerWrapper$2.run(LanguageServerWrapper.java:407)
	at org.eclipse.core.internal.jobs.Worker.run(Worker.java:63)

and because of the NPE random tests seem to fail.

@sebthom sebthom force-pushed the npe branch 2 times, most recently from dbac7c9 to 664f289 Compare May 3, 2024 20:57
@sebthom sebthom requested review from rubenporras and mickaelistria and removed request for rubenporras May 3, 2024 21:21
@mickaelistria
Copy link
Contributor

The tests failures are all related?

@sebthom
Copy link
Member Author

sebthom commented May 6, 2024

No, we are getting random OOMs for builds since 26th of April https://ci.eclipse.org/lsp4e/job/lsp4e-github/job/PR-975/4/. No idea why. I opened a ticket but they say it must be a config change in our build process.

When running the test suite on Windows a lot of NPEs with the following
stacktrace are thrown:
```
java.lang.NullPointerException: Cannot invoke
"org.eclipse.core.runtime.IProgressMonitor.done()" because
"this.this$0.initializeFutureMonitor" is null
	at org.eclipse.lsp4e.LanguageServerWrapper$2.run(LanguageServerWrapper.java:407)
	at org.eclipse.core.internal.jobs.Worker.run(Worker.java:63)
```
and because of the NPE random tests seem to fail.
@sebthom
Copy link
Member Author

sebthom commented May 7, 2024

@mickaelistria @rubenporras any objections to merge this?

return new Job(NLS.bind(Messages.initializeLanguageServer_job, serverDefinition.label)) {
@Override
protected IStatus run(IProgressMonitor monitor) {
initializeFutureMonitor = SubMonitor.convert(monitor, initializeFutureNumberOfStages);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe it is a silly question, but do we need an AtomicReference? Could we not achieve the same by saving initializeFutureMonitor to a local variable in line 394 (and also on line 382) before saving it to the class field, and then mark the monitor as done using the local variable?

Is there a benefit of AtomicReference over the local variable?

Copy link
Member Author

@sebthom sebthom May 8, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As far as I see it, at a minimum the initializeFutureMonitor needs to be made volatile because it is accessed from two different threads and the Job in createInitializeLanguageServerJob otherwise may never see the assigned value. The nice part of AtomicReference is that it offers compareAndSet() which can avoid another type of race conditions when the wrapper is stopped and restarted in quick succession. Also I find working with AtomicReference is more expressive regarding the intention than dealing with a volatile field.

Copy link
Contributor

@rubenporras rubenporras left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks

@rubenporras rubenporras merged commit 4e5a769 into eclipse:master May 8, 2024
2 checks passed
@sebthom sebthom deleted the npe branch May 8, 2024 20:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants