This is an archive of the discontinued LLVM Phabricator instance.

[analyzer] Add a thin abstraction layer between libCrossTU and libAnalysis.
ClosedPublic

Authored by NoQ on Dec 1 2020, 2:14 PM.

Details

Summary

After like ~three reverts of D67422, the last known problem with that patch is a circular dependency that that patch introduces: libCrossTU -> libFrontend -> libSema -> libAnalysis -> libCrossTU. Namely, D67422 causes libAnalysis to depend on libCrossTU due to PlistDiagnosticConsumer (which is moved into libAnalysis in that patch) potentially requiring cross-TU macro expansion information to bundle with the plist.

Circular dependencies are bad because they're not allowed under -DBUILD_SHARED_LIBS. It's likely that this problem can be resolved purely on cmake side and i simply wasn't trying hard enough to find a solution (on the other hand, say, libTooling had to deal with this by introducing libToolingCore - a smaller sub-library with less dependencies).

But, anyway, given that the dependency is extremely tiny, i suggest resolving it by adding a tiny abstraction layer that'd eliminate the dependency entirely. Namely, i'd like to add a virtual interface under CrossTranslationUnitContext. Such interface is defined in libAnalysis and implemented by the CrossTranslationUnitContext class in libCrossTU. This vaguely makes sense because libAnalysis is a low-level collection of analysis algorithms whereas libCrossTU is high-level, even frontend-level management of entire clang invocations so calling from libAnalysis to libCrossTU feels like layering violation.

In this patch i add only one function to the interface. If you guys want i can move all (or at least some) public methods of CrossTranslationUnitContext into that interface but there's no immediate need for that.

Diff Detail

Event Timeline

NoQ created this revision.Dec 1 2020, 2:14 PM
NoQ requested review of this revision.Dec 1 2020, 2:14 PM
NoQ updated this revision to Diff 308771.Dec 1 2020, 2:16 PM

Whoops, fix typos in header formalities.

xazax.hun accepted this revision.Dec 2 2020, 3:47 AM

LGTM!

This revision is now accepted and ready to land.Dec 2 2020, 3:47 AM
martong accepted this revision.Dec 2 2020, 4:05 AM

Looks good, thanks!

martong added inline comments.Dec 9 2020, 3:33 AM
clang/include/clang/CrossTU/CrossTranslationUnit.h
124

Why don't we have a dependency in libCrossTU to libAnalysis? In the CMakeLists.txt?
Here we implement the CrossTUAnalysisHelper's abstract virtual function thus we include the CrossTUAnalysisHelper.h. But
CMake should know about the dependency even if this is only a header only dependency, shouldn't it? (We were talking about this with @steakhal.)

steakhal added inline comments.Dec 9 2020, 3:58 AM
clang/include/clang/CrossTU/CrossTranslationUnit.h
124

IMO if a library (A) does not depend on another library (B), that means we can safely delete all files of the B and still be able to compile and run the A.
In this case, it won't, as the given header lives under B. So to make sure this principle works, we should state the dependency on B in A.


In our case, it means that libCrossTU depends on libAnalysis, as the CrossTUAnalysisHelper lives in libAnalysis which is used by libCrossTU to implement the CrossTranslationUnitContext.

NoQ added inline comments.Dec 9 2020, 10:02 AM
clang/include/clang/CrossTU/CrossTranslationUnit.h
124

There's already an indirect dependency (you have to look at all those CMakeLists.txt in order to notice it): libCrossTU -> libFrontend -> libSema -> libAnalysis (and a few other paths through the dependency graph). There's no harm in writing it down explicitly but there's also no explicit need and i'd rather have it not specified directly (if there's too little dependencies it'll warn us) than to specify too much by accident (there's no warning for unused dependencies and if a dependency eventually becomes unused it may accidentally prevent people from adding the dependencies they actually need).

steakhal added inline comments.Dec 9 2020, 10:50 AM
clang/include/clang/CrossTU/CrossTranslationUnit.h
124

Thank you for the explanation.

Herald added a project: Restricted Project. · View Herald TranscriptDec 10 2020, 11:03 AM
NoQ added inline comments.Dec 11 2020, 11:09 AM
clang/lib/Analysis/PlistPathDiagnosticConsumer.cpp
993

We were reverted because there's still a dependency on ASTUnit which lives in libFrontend. I guess i'll simplify the virtual method to return (MacroLoc, PPToUse) directly (?) (the old method will still remain on CrossTranslationUnitContext).

steakhal added inline comments.Dec 11 2020, 11:49 AM
clang/lib/Analysis/PlistPathDiagnosticConsumer.cpp
993

I don't see much uses of this function in the codebase. Why do you think it worth keeping it?

As a side-note, I'm planning to upstream some serious changes in macro expansion handling. Which will change the highlighted parts, probably resolving this circular dependency too.
Let me polish my work, and expect the patch on monday or tuesday.