This is an archive of the discontinued LLVM Phabricator instance.

[clangd] Wire up ASTUnit and publish diagnostics with it.
ClosedPublic

Authored by bkramer on Feb 13 2017, 2:29 AM.

Event Timeline

bkramer created this revision.Feb 13 2017, 2:29 AM
cierpuchaw added inline comments.
clangd/DocumentStore.h
42–49

Shouldn't this be called under a lock_guard?

cierpuchaw added inline comments.Feb 13 2017, 7:30 AM
clangd/DocumentStore.h
42–49

I should've reworded my comment before submitting it. By 'this' I'm referring to the 'Docs.erase()' part, not the whole function.

ioeric added a subscriber: ioeric.Feb 13 2017, 8:10 AM
ioeric added inline comments.
clangd/ASTManager.cpp
22

Any reason not to wrap code in namespaces instead?

krasimir added inline comments.Feb 13 2017, 8:34 AM
clangd/DocumentStore.h
42–49

Even under a guard, it may potentially still be unsafe since workers may operate on erased/modified StringRef-s.

51–66

StringRef doesn't own the underlying data, right? What if I erase it in the meantime?

78

Same thing, shouldn't these be strings?

arphaman added inline comments.
clangd/ASTManager.cpp
70

This is just a suggestion based on personal opinion: RequestIsPending and Done can be merged into one enum value that uses an enum like this:

enum ASTManagerState {
  Waiting, ReceivedRequest, Done
}

Then this condition could be rewritten as if (state == Waiting).

71

I believe std::condition_variable may also be unblocked spuriously when wait is called without a predicate, which would lead to an empty File down below.

clangd/ASTManager.h
68

It looks like Done is always accessed in a scope where RequestLock is locked, so atomic doesn't seem needed here.

krasimir added inline comments.Feb 14 2017, 3:40 AM
clangd/ASTManager.cpp
149

Do you have an idea about a proper error handling if Error?

163

Then maybe we need a big disclaimer comment at the declaration of createASTUnitForFile?

clangd/ClangDMain.cpp
32

Why not directly Store.addListener(llvm::make_unique<ASTManager>(Out, Store));?

clangd/DocumentStore.h
39

Is only the main thread supposed to addDocument-s? Otherwise the listener notifications might need to be guarded.

klimek added inline comments.Feb 14 2017, 7:04 AM
clangd/ASTManager.cpp
70

I'm not so sure. Once we have a queue (iff we ever get a queue), the "request available" is an attribute of the queue, while the "we need to exit" is an attribute of the system.

71

Yep, +1, the general pattern is to put while loops around.
It might actually be simpler to write that with a queue from the start (note that this would make the request queueing side somewhat less simple):

... Lock(RequestLock);
while (Requests.empty() && !Done) {
  ClangRequestCV.wait(Lock);
}
if (Done) return;
File = Request.pop_front();
ClangRequestCV.notify_all();
...

the while loop  can be written somewhat simpler with the pred version:
ClangRequestCV.wait(Lock, [&] { return !Request.empty() || Done; });
117

One question is whether we want to couple this to JSON, or have structured output that we serialize.
(I'm happy with doing this now, and refining later - doesn't seem super hard to switch)

clangd/ASTManager.h
35

At a first glance, it's weird that we have a global document store, but get a document store for each notification. This at least needs documentation.

68

Yea, after only having read this header, it looks like we might want to pull out a Request as an abstraction.

clangd/ClangDMain.cpp
32

Why's the ASTManager not on the stack?

clangd/DocumentStore.h
39

It would always be the responsibility of the callee to guard.

42–49

That depends on the guarantees made, and when we create copies :)

bkramer updated this revision to Diff 88515.Feb 15 2017, 5:42 AM
bkramer marked 16 inline comments as done.
  • Address review comments.
clangd/ASTManager.cpp
22

I don't really have an opinion one way or the other, but this seems to be the preferred way of doing this in LLVM.

71

Added the lambda. The current state is pretty weird, but making it a queue just to drop random elements from that queue is even weirder :(

149

For now I'll send it to logs()

clangd/ASTManager.h
35

This is leftover from an earlier design. Removed.

68

Wrapped all the guarded variables in a struct.

clangd/ClangDMain.cpp
32

Fixed. Lifetime is no longer managed by the DocumentStore (that was a bit weird)

clangd/DocumentStore.h
39

Added guard for now.

42–49

Added guard.

51–66

I guess it makes sense to create copies here. Somewhat sad but safe.

78

Done.

cierpuchaw added inline comments.Feb 15 2017, 5:55 AM
clangd/DocumentStore.h
42–49

'Docs.erase(Uri);' is still outside the critical section. It's easy to miss because of its placement directly after '{'.

bkramer updated this revision to Diff 88522.Feb 15 2017, 6:37 AM
  • Do not lock while running DocumentStore callbacks
  • Replace fake queue with a real queue (but it still has at most one element.
klimek added inline comments.Feb 15 2017, 6:48 AM
clangd/ASTManager.h
68

For me that actually makes it worse (sorry): I now read "Request.Done" and think the request is done :)

bkramer updated this revision to Diff 88523.Feb 15 2017, 6:54 AM
  • Inline the request struct again.
klimek accepted this revision.Feb 15 2017, 7:00 AM

lg

clangd/ASTManager.cpp
138–139

deque has resize *ducks and runs*

This revision is now accepted and ready to land.Feb 15 2017, 7:00 AM
krasimir accepted this revision.Feb 15 2017, 7:02 AM
This revision was automatically updated to reflect the committed changes.