-
Notifications
You must be signed in to change notification settings - Fork 17
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
Support header context #4
Comments
Overall, we want to achieve the following effect: assuming both Possible challenges: Could we still build preamble for header with given context?The answer is yes, the only thing we need to do is computing preamble bounds ourselves. For example, assume we have following file: #include <string>
#include <vector>
// ... a lot of code
#include <user.h> <=
// ... a lot of code The target header file is inside auto& completion = instance->getFrontendOpts().CodeCompletionAt;
completion.FileName = filepath;
completion.Line = line;
completion.Column = column; The filepath is the header file path(for clangd, it is main file). Then it can work perfectly. And code completion will cut off the source file automatically, so we don't need to any other thing. How server maintain the state of multi contexts?For every header file, unlike TU, server will use a Besides, providing extension requests: How can we find all possible header contexts for one file?
Further improvement
|
And it's possible that a header file is included multiple times in one source file. For a header file with guard macro or For example: // test.h
struct X;
// test2.h
#include "test.h"
// test.cpp
#include "test.h"
#include "test2.h" We will get two By the way, there is also a function called |
Issues in clangd:
What
#include
in C/C++ does is just simply copying the included file contexts to its location. Only.c/.cpp
(Translation Unit, i.e, TU) files will participate in the final compilation process and occur incompile_commands.json
with corresponding command.As we all know, clangd is clang based, we need to run clang frontend for given source file to get AST or code completion. Then,
we could response LSP requests. For cpp files, it's trivial. We just need to complie it as normal in clang driver. The only difference is we only generate AST no further step to generate LLVM IR.
But what about header files? How clangd deal with header files? clangd just regards a header file as a translation unit, and generate AST for it. Compilation commands are guessed from source file, e.g. based on file name match. The simple way works, but is totally incomplete!
Since a header file is only part of the source file, its AST is likely dependent on the preceding text and may have different ASTs in different translation units. For example:
It's obvious that
a.h
has different AST inb.cpp
andc.cpp
Currently, clangd can only get the AST inc.cpp
, i.e, treats it as a single TU. Another more extreme example is non self-contained header file(file cannot be complied individually). In above the file, though only one AST will be used, at least it can work. Consider following example:clangd will emit compilation error for
a.h
, because it cannot find the definition ofX
, which is defined in its header context--b.cpp
.This could be really frustrating. We should support check, lookup and switch context of header file!
The text was updated successfully, but these errors were encountered: