Wednesday, February 22, 2012

Advanced Embedded C++ Development with Arduino II

One of the techniques for managing growing code bases that I haven't been able to make work with the Arduino IDE in my Amigo project is hierarchical header file directories. Once you start combining code bases from a variety of sources, eventually you will run into two bases that use a header file by the same name, for example Display.h. In the case of Arduino, the conflict isn't in the file system -- the source code for each Arduino library is already separated into its own subdirectory -- but in how the #include statement is coded by the developer: the statement

#include <Display.h>

will be ambiguous as to which library you mean.

In Up the Source Code Organization I illustrated a way to handle this: by imposing the same convention I use for C++ namespaces and C preprocessor symbols, where I incorporate Digital Aggregates' domain name, for header file path names. This results in #include statements that look something like (as a completely fictional example)

#include <com/diag/amigo/Display.h>
#include <cc/arduino/Display.h>

such that my LC100 library would keep its header files in a com/diag/amigo subdirectory in its library directory, while would keep its header files in a cc/arduino subdirectory in its own library directory. This has the added advantage that all of the header file directory trees could be merged into a common /usr/include-like directory tree if that proved advantageous in the future. A similar convention is already being used to manage the growing /usr/include directory tree in various Linux/GNU distributions.

Currently the Import Library function in the Arduino IDE doesn't grok this kind of directory structure so that it uses the appropriate -Idirectory option, which tells the GNU C++ compiler where in the file system to start looking for header files, when the IDE generates the commands to build an Arduino application. How could it do so? I'm not really qualified to have an opinion on this, but maybe something as simple as the Import Library function doing a deeper search in the library directory and generating #include statements that include the relative paths of all the header files it finds. This wouldn't change how it is used today with existing libraries, and in fact would generate the same -I option for the compiler as it does now regardless of the header file organization. But it would permit a more complex organization in the future.

It is tempting to say that Arduino is too small to need this kind of organization, but I can see that this is already not the case in my own development. And when you start contemplating applications for the Arduino Mega-class boards, which have serious resources available to support quite complex applications, this is going to become even more of a problem.

No comments: