How can I see offending files with circular dependencies?

Hello all,

I’m creating some libraries for a project but I’m having warnings regarding circular dependencies. Is there a way to tell pio to show the files that cause that problem? Increasing verbosity does not work and I haven’t found how to do this in the documentation.

Thanks in advance.

Hi @punkto,
The Library Dependency Finder might come to your rescue here. It scans all headers for includes and lists them as part of your build process. You should be able to see cyclic dependencies in the tree like this:

My personal recommendation would be to search all files for missing #ifdefs and add them as necessary. Multiple superficial #include directives are a typical source of cyclic dependency issues.
See here for more reference on this matter.
Hope I could help

Thanks, @schallbert !

I’m sorry I didn’t mention that I already can see dependencies using LDF. I run pio in verbose mode, so I can see the dependency graph as well as cyclic dependencies warnings. The LDF must know the concrete files/includes that make a dependency cyclic so it can print the warnings. My point is that I don’t see a way ask the LDF to print more specific information about that warning (I’m thinking in how GCC prints errors/warnings, with the offending file and line). In case that this cannot be done, I think that this feature could be interesting for developers.


I see your point. You mean e.g. LDF dependency tree should mark files involved in a cyclic dependency red or so? I’d have to look at the repository to see how LDF is currently working and whether that’s an option to add.

This exactly.

That would be great! Thanks a lot!

OK, I found the code segments in platformio-core/
It’s about two methods, one recursively gets the library dependencies (search_deps_recursive()) and the other one prints the dependency tree, privat method (_print_deps_tree()).
The target now is to identify cyclic includes in the former and mark them in the latter.
I cannot promise that I find the time to create the solution for this in the near future but I’ll definetely keep this the back of in my head.
Cheers, Schallbert

OK, I just checked the current behavior.

Analysis result:

  • PIO only lists dependencies on a folder level. E.g. files directly created in /lib will be ignored in the Dependency graph.
  • I have created a direct circle between A and B. Due to the folder structure, PIO will draw an incomplete tree in case of a dependency because this tree would have infinite branches due to the cyclic dependency (because it is really a graph.
  • As the Dependency tree creation doesn’t use the compiler, it will not detect cyclic dependencies as of now.

I’ll have to have a deep-dive look at why the dependency finder does not show cyclics at the moment.


I’m also making some tests, cloning the platformio-core repo and seeing if I can understand enough to be of some help.

I’m using this repo with circular dependencies GitHub - punkto/pio_project_with_circular_dependencies

I got this:

$ ▶ platformio run -v
Processing native (platform: native)
LDF: Library Dependency Finder ->
LDF Modes: Finder ~ chain, Compatibility ~ soft
Found 2 compatible libraries
Scanning dependencies...
Warning! Circular dependencies detected between `/home/jorge/sandbox/programacion/python/pio_dev_test_repos/pio_project_with_circular_dependencies/lib/two` and `/home/jorge/sandbox/programacion/python/pio_dev_test_repos/pio_project_with_circular_dependencies/lib/one`
Dependency Graph
|-- <one> ([...]/pio_project_with_circular_dependencies/lib/one)
|   |-- <two> ([...]/pio_project_with_circular_dependencies/lib/two)
|-- <two> ([...]/pio_project_with_circular_dependencies/lib/two)
Building in release mode
g++ -o .pio/build/native/src/main.o -c -DPLATFORMIO=50204 -Iinclude -Isrc -Ilib/two -Ilib/one src/main.cpp
g++ -o .pio/build/native/program .pio/build/native/src/main.o -L.pio/build/native
============================================================ [SUCCESS] Took 0.51 seconds ============================================================

I’m having some trouble launching the debugger so far, so I can’t see yet the data the dependency finder holds.