Today I found out I can include and compile files mentioned like this:
#include "comm/UART_thingies.h"
, i.e. I can reach a file in a comm subfolder. It's not visible on the editor, but it's reachable.
It works:
Both on Linux and Windows.
Both with Arduino IDE 2.x and 1.x.
But! Around 2020 there were plenty of topics around here stating that subfolders in a sketch folder must be placed inside a subfolder named src, no exceptions. Therefore my experience contradicts those statements.
Does it mean that the devs have in a certain moment omitted the requirement for a presence of a subfolder named src and let us include files from whatever subfolders we want?
This is strange, I cannot include any header from src/header_1.h, but I do can do it from code/header_1.h.
UPD: include works if there're no .cpp files in the same folder. Weird.
UPD 2: nevermind, I sorted it out. Indeed, as you said, including .h files works alright from any folder. And .ccp files inside an src subfolder do get compiled (while .cpp files outside such subfolder do not).
What's more, ALL the cpp files in the src folder get compiled, regardless of whether or not they end up being linked to. So if there's an error even in some file you're not using, it will still get thrown at compile.
a C/C++ executable results from linking a runtime with a main module, and any additional modules that are referenced.
a module generally results from a single source file; usually with a .cpp extension, but some others are supported
.ino is a specific exception: all such files in the sketch directory are glued together and some extra magic is done to create the main module.
each source file has a corresponding header, which declares what's in the module
the implementation in the source file must conform to that declaration to fulfill that contract
consumers of the module rely on that declaration so that the implementation can be linked
headers are used via a preprocessor #include, which at its core finds text and inserts it in that place
For Arduino sketches, the linker joins
the main module from the .ino file(s)
modules from libraries
modules from compiling all the C++ source files in the sketch folder
its src directory
and all its subdirectories recursively
When using #include, you can reference any file anywhere, and that part will work. But if that header has a corresponding implementation -- almost always the case -- then the corresponding module must be known to the linker, usually because the compiler just built it (or it used a cached result).
As you have surely seen, the header is usually in the same directory as the source file, but that's not actually required.