Reputation: 23
Is using #include "component.c" considered bad practice or is there any misra standard rule violation? (potentially rule 3-3-1)
So far, I understand that it is a commonly categorized as bad practice but can be used in certain scenarios, would it be any particular concern for safety-critical applications?
Misra rule 3-3-1 states that Objects or functions with external linkage shall be declared in a header file
Upvotes: 0
Views: 1149
Reputation: 2312
Rule 3-1-1 is a MISRA C++:2008 rule
The applicable MISRA C:2012 guidelines are (probably) Rules 20.2 and 20.3 - which do not prohibit the use of .c
extensions.
--
In MISRA C:2004, Rule 8.5 prohibited source code in a header file (assumed to be a .h
file). This Rule was dropped for MISRA C:2012 to permit the use of inline
functions.
--
Personally, I think #include
-ing a .c
file is a bad idea - it suggests a mis-understanding of the language, the compiler and the linker.
If you do so, the expanded file would count as a Single Translation Unit for analysis purposes...
(see profile for Affiliation)
Upvotes: 0
Reputation: 180266
Is using #include "component.c" considered bad practice
Generally speaking, yes.
Usually, the preprocessor's file-inclusion feature is reserved to support factoring common declarations into their own files, so that they don't need to be duplicated in multiple sources. Such factoring provides huge benefits for maintainability in all but the smallest projects, and it is a near-requirement for libraries to be usable. A file containing only such declarations is conventionally called a "header", and is conventionally named with a .h
suffix. In this sense, then, the issue is partially about file naming and programming patterns.
On the other hand, C source files containing function or object definitions (as opposed to declarations) are conventionally named with a .c
suffix. The C language forbids multiple external definitions of the same identifier (function or variable name) in the same program, so such .c
files cannot be #include
d into more than one translation unit contributing to a program, and if they are included into even one, then they must not also be compiled directly. The usual way to build a program from multiple .c
files is to compile them independently and then link them together.
Provided one is sure to avoid duplicate definitions, it is not inherently wrong to #include
one .c
file into another. But this makes sense only as a special-purpose arrangement. It creates extra risk, and it provides no particular advantage as far as the language specification goes. Also, because it runs contrary to convention, it tends to surprise and confuse developers -- maybe even more experienced future you.
is there any misra standard rule violation? (potentially rule 3-3-1)
It does not inherently violate MISRA rule 3-3-1, but it makes it less painful to write code that does violate that rule. That is by making it feasible to have all the needed external declarations in a single .c file plus its inclusions, instead of providing a separate header.
I don't see any other MISRA-2012 rule that such an inclusion would violate. But that would not hold much water with me in code review.
Upvotes: 0
Reputation:
You are referencing the MISRA C++ standard not the MISRA C standard. In the MISRA C++ standard rule 3-1-1 does not restrict you from #include-ing C files in other C files, because any C file may include one another and not declare anything as having external linkage. The rule/requirement is about external linkage, not about C file inclusion. I believe that if they were to add a rule for including other C files it would be under section "Source file inclusion" rules 16-2-X, but i have just checked and there is nothing about including other C files. Personally, i dont mind including other C files because i see #include as just a copying and pasting operations to be used however you see fit.
Upvotes: 1
Reputation: 30
It is also a matter of security in terms that you might not want to provide your code, so you just give the header and the object files
Upvotes: 0
Reputation: 2671
When you write a program like that, it is called a unity build. A good example of such a program is the compiler for the Odin programming language. So it can be done, but like anything else, there are tradeoffs.
It puts more source into a single translation unit. This can help optimization, similar to how link-time-optimization works since the compiler can actually see the source from functions in other C files.
Less clutter in project files (less headers), and therefor, less repetition.
A greatly simplified build; It may be as easy as building only one file even if many files are in the project.
Harder to understand for co-workers who use more common practices.
You can no longer define a static variable with a very generic name in a C file, because that C file could be part of a bigger translation unit. You will wind up with more verbose variable names.
It will generally slow down the build. Build systems (like make), can speed up compilation by only re-compiling what is dependent on all changes. If you are combining things into a single translation unit, the whole thing will need to build for every change. In a big project, this will lead to more memory consumption during the build.
You cannot parallelize the build.
I don't actually know, but it doesn't violate the rule you posted:
Misra rule 3-3-1 states that Objects or functions with external linkage shall be declared in a header file
By including a C file, you know longer have external linkage because they are in the same translation unit.
Upvotes: 1