If you have a lot of different languages in the same repo (like a monorepo scenario), you might be better served using something like bazel. It'll abstract away all the language-specific build systems, for better or worse, and make it a bit more uniform to manage. It's not a panacea--basically everything now has a single annoying build system instead of everything having an annoyingly different native build system.
Well I was hinting at it, or the other similar systems (gn, buck, pants, etc.) - you end up needing a language-agnostic (or rather say, language-diverse system) that understand how these compilers / runtimes express output artifacts and actions. It's not always that easy (e.g. "virtual_includes" in bazel and `#pragma once` do not work well, but it's small price to pay (e.g. go back to #ifndef MY_HEADER_H #define it)).