MaskRay / ccls

C/C++/ObjC language server supporting cross references, hierarchies, completion and semantic highlighting
Apache License 2.0
3.73k stars 254 forks source link

Can't use Homebrew's `gcc` as the language of `ccls` on macOS #897

Closed damiannmm closed 2 years ago

damiannmm commented 2 years ago

Observed behavior

Doing #include <bits/stdc++.h>, scanf(), and printf() shows err, despite it works without err when compiling; using std as namespace also raises warning.

Screen Shot 2022-08-07 at 1 25 37 PM

I suspected that this happened because ccls uses clang while I tried to compile with g++-12; as of now, I still can't find out how to customize ccls so it uses the binary that I wanted.

Already tweaks ~/.ccls and compile_commands.json to no avail.

Expected behavior

There should be no err nor warning.

Steps to reproduce

  1. Install gcc and ccls via homebrew, $ brew install gcc ccls
  2. $ vi a.cpp with content similar to,
#include <bits/stdc++.h>  // the bits/... shows err, file not found

using namespace std;  // std gives warning, implicitly-defined namespace

int main(int argc, char *argv[]) {
    printf("Hello world!");  // printf also shows err, undeclared identifier
    return 0;
}
  1. $ g++-12 -std=c++17 a.cpp gives no err.

System information

$ brew install ccls
...
Warning: ccls 0.20220729 is already installed and up-to-date.
...

$ ccls --version
Homebrew ccls version <unknown>
clang version 14.0.6
$ clang --version
Apple clang version 12.0.0 (clang-1200.0.32.29)
...

$ g++-12 --version
g++-12 (Homebrew GCC 12.1.0) 12.1.0
...
damiannmm commented 2 years ago

Working as intended on Ubuntu WSL, installed the ccls via apt-get,

$ sudo apt-get install ccls

Annotation 2022-08-07 144907

Coding and compiling (with $ g++ -std=c++17 a.cpp) shows no err nor warning on Ubuntu WSL.

System information

$ ccls --version
ccls version 0.20190823.6-1~ubuntu1.20.04.1
clang version 10.0.0-4ubuntu1
$ which clang  # returns nothing

$ g++ --version
g++ (Ubuntu 9.3.0-17ubuntu1~20.04) 9.3.0
...
FederAndInk commented 2 years ago

#include <bits/stdc++.h> is not standard C++, try using the standard headers.

damiannmm commented 2 years ago

Yes, and that's what I'm currently trying to make it work for. It worked fine on Ubuntu WSL but didn't on macOS. I even tried adding the header by make a softlink from Homebrew's gcc of bits dir to macOS' clang, but it still didn't work.

$ ln -s /usr/local/Cellar/gcc/.../bits/ /Library/Developer/.../c++/v1/bits

Is there any way tweak the .ccls so it uses the brew's installed g++-12 instead of macOS' clang? Or do I have to tweak it on NVIM's or coc's settings?

madscientist commented 2 years ago

I'm not sure what you mean by "use g++". ccls doesn't "use" any compiler per se. It's a separate program that parses C++ code to provide an LSP server. It could be written using an entirely stand-alone C++ parser but that would be a lot of duplication of effort, so instead ccls links in the clang project's C++ parser. This means that ccls parses content in the same way that clang does, but it doesn't really run the clang compiler that you have installed.

If you wanted a program that linked the C++ parser from the GCC compiler to parse your C++ code, instead of clang's, then that could be created (I don't know of one that exists today) but it would be a completely different project, not ccls.

If you are using non-standard header files, that the compiler you're using somehow knows how to find without you having to add -I options to the compile line, then you have to tell ccls where to look for those directly by adding -I options.

damiannmm commented 2 years ago

I'll try adding the -I options as soon as I'm back on the cpp project. Let me know if I'm wrong, but that should be on the .ccls file, right?

Thanks!

FederAndInk commented 2 years ago

yes, its all explained in the wiki: https://github.com/MaskRay/ccls/wiki/Project-Setup#ccls-file

it should be something like:

%hpp

-isystem/path/to/bits/includedir

you can also put a stdc++.h like header in your project and include it instead, like: https://gist.github.com/Tlapesium/d6b01ac194729799b35b2fb5a015ba95

madscientist commented 2 years ago

I don't think you want to limit this to just header files via %hpp do you?

FederAndInk commented 2 years ago

yes, you are right, just remove the %hpp

FederAndInk commented 2 years ago

but, I'd rather make a stdc++.h in my project, so its compatible with all compilers and standard c++, and you don't have to tell ccls where to look for it

(or just use the standard headers, avoiding compiling all std)

damiannmm commented 2 years ago

I think it's solved now; here's my .ccls,

$ cat .ccls
clang
-isystem/Library/Developer/CommandLineTools/usr/include/c++/v1
-isystem/usr/local/Cellar/gcc/12.1.0/include/c++/12/x86_64-apple-darwin19

and voila, everything works as expected.

Thanks a lot to @madscientist and @FederAndInk!