Swift + VSCode + CMake: SourceKit can't find module-mapped dependency

Hey all,

I am setting up a Swift project in VS Code, using CMake as the build system, and I'm encountering an issue where SourceKit in the VS Code extension can't detect a module-mapped C/C++ library. Everything builds and runs as expected, but in the editor, SourceKit gives me the message "No such module 'Dependency'".

I've set up a tiny/MVP reproduction repo: GitHub - davidrpiper/SwiftCmakeModulemapMVP

The dependency is a tiny C project (built as a dylib) that I've added as a git submodule.

No matter what I do with the module.modulemap file for the dependency, I can't get SourceKit to pick it up.

Moving the module map directly into the dependency directory (and updating header path) also builds and runs, provided that I include the dependency directory with CMake's target_include_directories. But still no SourceKit recognition.

Hoping to find out if I'm doing something wrong, or if I'm hitting one of the edges of what's possible in VS Code at the moment. Either way, keen to see Swift expanding into new environments like this!

Does setting set(CMAKE_EXPORT_COMPILE_COMMANDS ON) in your CMake fix the issue? That way SourceKit-LSP can load the compiler arguments (and thus search path) that are used to build the files from the generated compile_commands.json.

If not, could you file an issue for this in GitHub - swiftlang/sourcekit-lsp: Language Server Protocol implementation for Swift and C-based languages and include the output of sourcekit-lsp diagnose in it?

Hey Alex, thank you for the quick response - yes that seems to have worked!

The compile_commands.json gets created in the build artifacts directory, and it generates commands in that file for the main project and the dependency.

However, Autocomplete, "Go To Definition" and "Go To Declaration", don't seem to work on the Swift side (both within Swift code and across the C/Swift boundary), even after a successful manual build-and-run from inside the IDE.

Even "Find All References", etc, turns up nothing, even though I made the second Swift file in the same src/ directory. Not sure if this problem rings any bells.

(Syntax Errors are also not picked up at all until I manually build, which suggests things are not auto-building in the background as expected. Possibly my VSCode config needs tweaking, will investigate.)

sourcekit-lsp diagnose is good to know about, thank you. I'll keep poking around and see if I can turn anything up. If not, will raise a GitHub ticket.

This is expected. Background indexing is only supported for SwiftPM projects. You need to build your CMake project to refresh the index.

Also from what you describe, I assume that you’re missing -index-store-path /some/path as a compiler argument in your CMake files. Adding that will make compilation create the index. It doesn’t matter which path you pass to -index-store-path, I would suggest something inside your build directory.

This is expected. Background indexing is only supported for SwiftPM projects. You need to build your CMake project to refresh the index.

Ah all good, this is fine for my purposes, glad it's not a config issue on my side.

I assume that you’re missing -index-store-path /some/path as a compiler argument in your CMake files. Adding that will make compilation create the index. It doesn’t matter which path you pass to -index-store-path, I would suggest something inside your build directory.

Adding target_compile_options(mvp PRIVATE -index-store-path "${CMAKE_BINARY_DIR}/$<CONFIGURATION>") creates a v5/ directory with symbols in (this case) the build/Debug directory.

However, SourceKit still doesn't seem to pick it up, even if I override the extension settings directly to pass the directory to sourcekit-lsp:

-index-store-path
/Users/.../SwiftCmakeModulemapMVP/build/Debug [or /v5]

Could you double-check that -index-store-path is in compile_commands.json and it’s pointing to a non-empty directory?

If that’s the case, could you file an issue for this in GitHub - swiftlang/sourcekit-lsp: Language Server Protocol implementation for Swift and C-based languages and include the output of sourcekit-lsp diagnose in it? I can look at the diagnose bundle that way and it should be able to tell us what’s going wrong.

Interestingly it looks like -index-store-path is not propagated to compile_commands.json...

Have raised an issue at Swift + VSCode + CMake: SourceKit can’t find module-mapped or Swift dependencies for code completion · Issue #2087 · swiftlang/sourcekit-lsp · GitHub - we can move conversation to there if easier; up to you as this feels like it could be a CMake problem still.

Thanks for filing the issue. Let’s continue the conversation there.

Just to circle back from the resolved ticket - the issue was that my CMake version was too low.

The solution was to either bump to version 3.29 or above, or explicitly set CMake Policy CMP0157 to NEW.

Thank you Alex and Evan for your help!