Chapter 12. Usage

The easiest way to start using eCos for C++ development is to use the special configuration template included in this release for this purpose. With command line configuration it may be used as in the following example for the Atmel EB40A target:

$ ecosconfig new eb40a libstdc++

If using the graphical tool, the template may be selected with the Build->Templates menu item.

Once the eCos libraries are configured and built, you may link your application. Be sure to append -lstdC++ to the end of the link line. If you wish to use C++ exceptions, be sure to either remove -fno-exceptions from your compilation line, or append -fexceptions at the end of the compilation line. Similarly, to use RTTI, either remove -fno-rtti from your compilation line, or append -frtti to the end of the compilation line. Finally, despite what some targets may have used for their default compiler flags it is important that the option -fvtable-gc is not used.

12.1. Requirements

As noted earlier, this package uses CDL to set constraints on the rest of the eCos system for correct and standards compliant operation of the C++ library. By selecting with the libstdc++ configuration template, you will be able to start with a configuration with all the necessary packages included and options set.

Building C++ programs, particularly those that use templates heavily (either directly, or using the templates from libstdc++), can take a lot of memory on the build machine - figures in excess of 220Mb have been observed building the testsuite included with this package. Be sure to have sufficient RAM to prevent extended build times.

This package requires a patched version of the GNU compiler in order to correctly support thread-safe C++ exceptions, and avoid problems with common infrastructure underlying most standard C++ library classes. Refer to the tools building notes below for further details.

[Warning]Warning

If a compiler is used which was not supplied by eCosCentric, nor built with eCosCentric's patch, the facilities provided by the standard C++ library will not be thread-safe. This may result in corruption, unexpected behaviour or a crash. In particular, C++ exceptions will not be thread-safe. Even if an application does not use exceptions directly, they may be used internally within the standard C++ library. Furthermore, certain infrastructure used by multiple C++ library objects (such as allocators) will also not be thread-safe.

The multi-thread protection provided by the standard C++ library intentionally only extends to subsystems shared by multiple classes. It does not mean that multiple threads can safely access individual object instances. If an individual object may be accessed by multiple threads simultaneously, access to that object will still need to be protected separately by the user at the application level, for example with a mutex. The thread-safety protection provided by the eCosCentric-enhanced version of the standard C++ library only ensures that threads can safely access different instances of C++ library objects without special protection by the user, despite many of these objects using functionality which requires shared global state. This approach is an intentional design decision in order to avoid unnecessary locking overhead.

Due partly to this specialised toolchain support it is not possible to use this package with the synthetic target, as native toolchains are built with specialised knowledge of the C++ runtime installed on the native OS. This is not solely due to the aforementioned patches, but also because of direct assumptions made as part of the GNU toolchain build procedure. As such, use under the synthetic target is unlikely ever to be possible.

It has been observed that GDB releases prior to GDB 6.1 can have difficulty debugging complex C++ applications, particularly those that extensively include template classes containing virtual functions. GDB 6.1 or above is recommended.

12.2. Issues to consider

12.2.1. Using C++ exceptions

There are a number of considerations when using C++ exceptions:

  1. Care should be taken when compiling C++ code with -fexceptions (the default). GNU C++ has been designed so that exceptions do not necessarily add overhead to functions. However they may add overhead in the following circumstances. Namely, when:

    1. Exceptions are actually used; OR
      1. The function (funcA) calls another function (funcB) with a non-null exception specifier or no exception specifier; AND
      2. that function (funcA) contains an automatic object; AND
      3. that object is defined to use a destructor, and would therefore need to have the destructor called if the called function (funcB) threw an exception through this stack frame.
  2. Not all eCos API functions have null exception specifiers yet, which may lead to very small unnecessary overhead when used from C functions in certain circumstances described earlier. Annotating all functions with null exception specifiers throughout the entirety of eCos is a massive job beyond the scope of the work done to provide C++ support. However many of the key APIs can be updated. In the current eCos sources, some obvious APIs have been updated such as all of the kernel C API and much of the ISO C/POSIX APIs.
  3. Exceptions thrown from signal handlers are not supported.
  4. Exceptions are not supported in ISRs, DSRs, nor ASRs. It is neither feasible nor sensible to support exceptions in ISRs or DSRs. Support for ASRs may be added at a future date, although there are no plans at present.
  5. Use of C++ support from this package can increase the thread stack requirements markedly. For example, if you use C++ exceptions, you should expect to add around 4Kbytes to your stack requirements for each thread which can throw exceptions. Developers may find it useful to enable kernel thread stack overflow checking (CYGFUN_KERNEL_THREADS_STACK_CHECKING and possibly also CYGFUN_KERNEL_ALL_THREADS_STACK_CHECKING), especially if erratic behaviour is observed in threads using C++ features.

12.2.2. Application size

It is widely acknowledged that when using C++ libraries, memory can quickly be consumed, particularly code (ROM/Flash) space. Small targets may have difficulty running even short C++ programs. For example, it is recommended to use the MEC01 memory extension card on the Atmel AT91 evaluation board platforms (EB40, EB40A, EB42, EB55) to provide extra space for applications. The eCosPro AT91EB40A port can take advantage of the MEC01 if eCos is configured with CYGHWR_HAL_ARM_AT91_EB40A_MEC01_RAM enabled.

Similarly, because of the generally larger code size, download times can be lengthy if using a slow transfer mechanism such as 38400 bps serial. Alternative download options such as ethernet or fast JTAG emulator should be considered for an efficient development/debug cycle.

It may be possible in future to reduce the code size overhead using linker garbage collection more fully. Currently linker garbage collection is not performed on the GNU standard C++ library itself. However it is anticipated the savings will turn out to be small.

12.2.3. C++ exceptions in callbacks

eCos itself is not built with exception support (-fexceptions) for the reasons given earlier concerning the overhead of exception support. As a consequence throwing exceptions from callbacks will not work, e.g. when using qsort(), bsearch(), etc. eCos does not yet support a means of building individual files with differing flags - flags are manipulated only for complete packages or by using custom build rules which would be unacceptable due to maintenance overheads.

12.2.4. Licensing

The GNU standard C++ library has its own license distinct from that of eCos. As a basis it uses, like eCos, the GNU General Public License. Also like eCos it includes an exception that permits the use of the library in proprietary applications. The exception is as follows:

As a special exception, you may use this file as part of a free software library without restriction. Specifically, if other files instantiate templates or use macros or inline functions from this file, or you compile this file and link it with other files to produce an executable, this file does not by itself cause the resulting executable to be covered by the GNU General Public License. This exception does not however invalidate any other reasons why the executable file might be covered by the GNU General Public License.

This exception is very similar to the eCos GPL exception, and is compatible with it. Further information on this license can be found in the C++Introduction of the libstdc++ online documentation set.

Most of the test files imported from the libstdc++ testsuite are covered by the full GPL without any exception. This means that distributing binaries of the test executables themselves gives a requirement to make available the full source code of that binary under the terms of the GPL. This is not considered an onerous obligation as distributing test binaries for this testsuite publically is unlikely to be a common requirement.

12.2.5. Standards Compliance

Versions of eCosPro which are shipped with GCC 7.3 or later are broadly compliant with the ISO/IEC 14882:2011 C++ standard (also known as C++11), albeit with some notable exceptions.

Information on GCC 7.3's standards compliance can be found at https://gcc.gnu.org/onlinedocs/gcc-7.3.0/gcc/Standards.html, or elsewhere on the same website for other GCC release versions.

In particular, there is more detail on the compliance efforts with the various C++ standards described at https://www.gnu.org/software/gcc/projects/cxx-status.html.

The C++11 standard in turn assumes that the library features of the system are compliant with the ISO/IEC 9899:1999 C standard (also known as C99). Information on eCosPro compliance with ISO C standards can be found in the relevant section of the eCos C and Math library documentation.

Futher notes on compliance with the C++11 standard are:

  • Any programs requiring C++11 library features must include the eCos package "ISO standard C++" (CYGPKG_LIBSTDCXX) in the eCos configuration, with the "C++ library support" (CYGPKG_LIBSTDCXX_LIBRARY) option enabled.
  • As noted earlier, a particularly notable divergence of eCos from the standards is the absence of most wide character support and functions.
  • The level of functionality and standards compliance of the clocks provided for use with the <chrono> header are highly dependent on the eCos configuration in use, such as the presence of the common clock package (CYGPKG_CLOCK_COMMON), POSIX clocks (CYGPKG_POSIX_CLOCKS) and/or the eCos wallclock subsystem (CYGPKG_IO_WALLCLOCK).

    Additionally the “steady_clock” is not provided in the eCosPro implementation, and any use of it will result in the normal system clock being used instead.

  • Although the C11 <complex.h> is not supported, the <complex> header defined by C++11 is.
  • At the time of writing, the thread support library portion of C++11 (section 30) provided by the headers <thread>, <mutex>, <shared_mutex>, <condition_variable> and <future> are not yet of production quality, and despite appearing to be usable in eCosPro, their use cannot yet be considered supportable.
  • C++ destructors for global C++ objects are not run on program exit.

12.2.6. Open issues

12.2.6.1. GCC 3.3.x issues

At this time there are only two significant known open issues that developers should be aware of which may impact development:

  • GCC 3.3.x misoptimizes code in functions with complex number parameters. The workaround is to compile without -O2 (or append -O0 to the end of the compile line). This issue has been filed with the GCC project as bug #15061. As a consequence of this compiler bug, the complex2 test in this package is likely to fail.
  • GCC 3.3.x fails to return NULL when using the std::nothrow variant of the new operator when an amount of memory is requested beyond what the system has available. Instead of NULL, 4 is returned. This is listed with the GCC project as bug #13215 and the problem is not going to be addressed in the GCC 3.3.x series. The problem is fixed in GCC 3.4. As a consequence of this compiler bug, the new1 test in this package will fail with GCC 3.3.x.

12.2.6.2. GCC 3.4.x issues

The only known issue affecting the use of GCC 3.4.x is specific to M68K/Coldfire, where the software floating point emulation is too imprecise, and causes a small number of tests within the libstdc++ package to fail, primarily those that test long double support.

12.2.6.3. Generic issues

It is worth mentioning that, as previously mentioned above, wide character support is not included. Support for wide characters may be developed in due course, but it would require significant development in the underlying eCos C library.