Clangd LSP Jump To Definition takes me to .h file

I utilize clangd server, setup correctly in the project with a compile_flags.txt. When I do jump to definition, it takes me to the header file defining the function, and pressing jumps to definition again gives me to the same point im already on (using FzfLua as handler).

but when I manually open the c file, jump to definition starts working correctly and takes me straight to the c file (for all the functions in this file). this is functional for the entire session of neovim, as in I can close the c file (buffer delete), but jump to definition still takes me straight to it instead of the header.

till I manually open the c files, clangd + Neovim LSP doesn’t jump to them. Ive been resorting to using ctags because that’s much more reliable for this use.

was wondering if this is a config issue or something:
(here is my clangd setup)

This is pretty much a technical limitation of clangd and the way c projects are compiled, when it only has a compile_flags.txt available.

With that, it can only analyze the single opened source file, including the #include header. On a goto definition call it can only go to the header file, as clangd does not know which .c file corresponds to the .h file.

clangd only obtains this information, when the .c file is loaded as well.

With compilation_commands.json it’s a different situation, because it contains the information about the .c <-> .h relations and clangd knows where to go directly.

This is not an issue of neovim AFAIK.

1 Like

Yeah, this makes sense, I anyways don’t experience this problem with CMakeLists.txt files to export compile_commands.json from. Im using a Makefile project right now, so best I could do myself was the compile_flags.txt file with the right includes and #defines.

this tool helped me generated compile_commands.json for each directory using just output from the Makefile:

You can also use BEAR to generate the compile_commands.json. I’ve used that successfully on all my GNUMake-based projects.