CleanC, from IMEC, is a new programming style for C code that substantially increases the parallelization and optimization potential for multiprocessor targets. The CleanC adherence analysis plug-ins are freely available through Eclipse. IMEC is developing multi-processor system-on-chip design tools to efficiently distribute applications over multiple processors while taking care of the synchronization of the tasks and the exchange of data between tasks.
IMEC’s mapping technology tool flow consists of parallelization and memory hierarchy optimization tools. To allow MPSoC design tools to fully unravel the intricacies of the application being analyzed, a number of restrictions are imposed on how the application is coded using the ANSI-C language. Therefore, the input code has to be written in so called CleanC, which is sequential C code written in a way that it is multiprocessor-friendly.
To enable software developers to develop code that is suitable for parallelization and mapping on multiprocessor platforms, IMEC is developing a code re-factoring toolbox. First, the application code is analyzed and violations of the CleanC programming style are flagged. To this end, CleanC adherence analysis plug-ins have been developed. Secondly, user guided code transformations are applied to the code to make it compliant to the CleanC programming style. To optimize this process, IMEC is currently developing interactive refactoring tools.
IMEC provides its CleanC adherence analysis plug-ins to the industry for free which will enable them to efficiently analyze their code. The CleanC tool is a plug-in for the Eclipse/CDT development environment for C and C++ applications. It extracts and visualizes the function call graph. The highly interactive CleanC environment allows for detection of fragments in sequential C code that are potentially hard to analyze by the MPSoC design tools and would lead to suboptimal solutions.
CleanC tool Features
- Distinguish source ?les from header ?les. Header files are for declarations, source files can define and declare items.
- Use macros for constants and conditional exclusion. The preprocessor engine of C is too powerful for its own good. We restricts its usage (as much as possible) to so-called object macros, useful for writing platform independent code.
- Keep variables local. No usage of global variables.
- Make sure a pointer points to only one data set. Do not use pointers to point to different data sets throughout its lifetime (e.g. to different arrays or to other entries within an array).
- Do not use recursive function calls.
- Do not use functions with varargs.
- Use switch statements instead of function pointers. Function pointers, especially anonymous function pointers, make C code very hard to understand for tools and humans alike.
- Use the manifest loop pattern. A manifest loop is a loop with an iterator which is initialized with a manifest value (a constant or value computed from iterators of outer loops), where the iterator is incremented or decremented with the same manifest value in each iteration, and where the loop ?nishes when the iterator reaches a certain manifest value.
- Make the control ?ow regular. Do not use break statements in loops, continue statements, goto statements, multiple return statements (unless in all of the difference branches of the same conditional) or break statements in anything but the last statement of a case statement.
- Keep side-effects out of expressions. Do not use side-effects within other expressions (e.g. incrementing a value while passing it as argument).
- Use indexes instead of pointer arithmetic.
- Do not cast to / from a pointer. Use casts properly, and do not cast a pointer type to a non-pointer type or the inverse (with the exception of casting arrays to pointer types with equal base types).
- Cast the result of malloc() to the correct type.
- Use arithmetic operators to perform calculations. Use proper arithmetic operators instead of bit operators as much as possible.
- Avoid the dark corners of the C standard. The C99 standard does not actually define what should happen with modulo or division with negative numbers, or volatile.
- Respect the semantics of types: While C is statically typed, user-defined types (typedefs) are only tye-checked according to the types they denote.
More info: CleanC Analysis Tools