As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.
No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.
"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]
When I asked about enums occupying memory, here is what I had in mind.
If I #define NextVal 10, then the only "memory" used is the same flash space that any numeric value would occupy. [nb: this statement is clearly true only for Harvard architectures where code occupies some nominally nonvolatile memory]
But, if I do
enum {
NextVal = 10,
};
What is the memory "footprint"? Does is live in SRAM? Is the memory footprint any different than
static const uint8_t NextVal = 10;
If used in a place where speed is critical, aren't there usually more operations to get it out of SRAM than from FLASH (especially if it is a single byte would otherwise be embedded in the (AVR) instruction)?
And, again, folks, I am not in any way critical of the suggestions and comments above; they are really appreciated. Just trying to compare and contrast (and learn).
Does not, all by itself, occupy memory. Memory occupancy is determined as it is used. But, the simple variable declaration, just shown, does occupy memory once you write
x = MaxVal;
And, in a Harvard architecture, that memory occupancy is SRAM rather than FLASH because MaxVal, here as a plain variable, can be altered at other points in the program. But, if I write
static const uint8_t NextVal = 10;
And use it thus:
x = MaxVal;
Does MaxVal live in SRAM or does it live in FLASH (again, Harvard architecture)? Is the "assignment" made at compile time (as a #define would be) or is it assigned at run time? The same question, then, of an enum. If MaxVal had been defined as an enum, and used in an assignment statement, does that value live in SRAM or does it live in FLASH? If (and, of course, this is a big "if") speed and memory footprint are important at a given point in the program, it seems to me that this would be useful information.
HOWEVER, this thread started out about MISRA, static code analysis, and, by inference, "safety". We know that type checking is an important aspect of safety. On the other hand, safety can include constants being in FLASH where we have a very high confidence level that nothing will alter them (no buffer over-runs, no stack overflows, no nothing!). And, by "FLASH", I don't mean p-strings, but the way the AVR op-codes embeds constants into the opcodes, the results then being in FLASH.
So, please, I am not trying to be argumentative, here. Quite the contrary. Trying to learn!
The case for using a name instead of a raw number is simple:
Documentation and the ease of making reliable changes.
Deciding between #define , static const int
and enum constants can be interesting.
@ka7ehk:
Unless MaxVal is global, the as-if rule allows the
compiler to do with MaxVal pretty much whatever it wants.
Even without help, the compiler will probably be
able to figure out whether MaxVal is ever changed.
If never changed, (uint8_t)10 will be quietly substituted for MaxVal.
MaxVal might be as-if-ed completely away.
Do not make a pointer to it.
x=MaxVal will probably become LDI Rx, 10 .
In C, no object may be used as the dimension of a global array.
In C++, your static const uint_t NextVal may be so used.
NextVal will almost certainly be as-if-ed away.
The necessary reasoning is required to allow its use as an array size.
Deciding between #define , static const int
and enum constants is not always interesting.
If you just want one number in the range -0x7FFF..0x7FFF
and do not need it in a constant expression,
use whatever makes you feel good.
If you need it for a constant expression, e.g. an array dimension,
in C, scratch static const int.
If you need a built-in type, scratch enum.
If you need it in assembly, use #define.
In C, IIRC the types of the enum constants are int (!!)
and sizeof(enum menage) == sizeof(int) .
Not sure about C++.
GNU has always had, since I've used it, the -fshort-enums compiler option. This causes enums to have the smallest int that can contain the enumerated values. In my code that is almost invariably an 8 bit int.
In the latest GNU and Microsoft C++ compilers, you can specify the size of the enums. I don't know about C compilers.
Over time we have used various other static code analysis tools (including cppcheck - which is both C and C++ despite the name) but these days we use the terror that is Klockwork:
Electronic Design
Improving Code Quality in the New Year
Are you going to reduce bugs and improve security and code quality in 2018?
In practice, sound static analyzers output an exhaustive list of places where the vulnerability could occur, most of which are false alarms or "false positives" that need to be reviewed.
While more demanding for users, these static analyzers make it possible to achieve higher levels of confidence than is possible with their unsound counterparts, which makes them attractive in a security context.
...
Definition of Sound Analysis
...
Costs and Benefits of Sound and Unsound Analysis
[first paragraph, bullets, second paragraph]
Depending on the technique used, they [sound analyses] may require code changes, user-supplied annotations, or reviews of numerous false alarms.
[remainder is on SPARK]
Conclusion
...
[last paragraph]
Thanks to its ease of deployment, unsound static analysis has become a standard tool in serious software development. It’s used in most large software companies, and advised by best practices. Due to its higher cost, sound static analysis has long been the domain of experts. However, with the recent progress in verification techniques, sound static analysis is used in more and more projects, and is becoming part of the standard development process when strong safety or security requirements are needed. In the years to come, sound static analysis may become a standard tool for critical software development.
P.S.
[end of second paragraph]
For example, Mozilla uses Clang Analyzer, clang-tidy, their own checkers, and Coverity on its C/C++ code.2
clang-tidy is a clang-based C++ “linter” tool. Its purpose is to provide an extensible framework for diagnosing and fixing typical programming errors, like style violations, interface misuse, or bugs that can be deduced via static analysis. clang-tidy is modular and provides a convenient interface for writing new checks.
Speaking about the MISRA rules, some analyzers check the compliance of the code with these standards (Coverity, Klocwork, Parasoft and others), and some - like PVS-Studio don’t. As the developers state in their blog...
MISRA added to PVS-Studio as blog'd on 10.12.2018 in addition to CWE and SEI CERT :
by Andrey Karpov (CTO, Program Verification Systems)
...
So initially we have been critical to the MISRA standards and haven't planned to introduce them for a long time.
...
Everything changed when in 2018 we've started supporting embedded systems. This year we supported the following features in the analyzer:
Windows. IAR Embedded Workbench, C/C++ Compiler for ARM C, C++
Windows/Linux. Keil µVision, DS-MDK, ARM Compiler 5/6 C, C++
Windows/Linux. Texas Instruments Code Composer Studio, ARM Code Generation Tools C, C++
Windows/Linux/macOS. GNU Arm Embedded Toolchain, Arm Embedded GCC compiler, C, C++
...
So now you can install or upgrade PVS-Studio and start using diagnostics based on rules from MISRA C and MISRA C++. The set of supported rules is incomplete, but it shouldn't be an obstacle to start using PVS-Studio.
...
[how to enable MISRA in PVS-Studio on Windows, macOS, and Linux]
...
P.S.
[how to for feedback]
...
PVS-Studio is now zero price for conditional FOSS (specific repositories, no mirrors) and conditional non-FOSS (ones as given (iow an individual) or in the specific role of student, specific comments in non-header source code files)
Dan Saks often writes wisely : http://www.embedded.com/electronics-blogs/programming-pointers/4023879/Enumeration-Constants-vs-Constant-Objects
EDIT: Note that the article is from 2001. While the principles still holds, the performance of compilers might have changed considerably.
As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.
No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.
"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]
- Log in or register to post comments
TopNote that "const objects" is one of the places where 'C' does differ from C++ !
Top Tips:
- Log in or register to post comments
TopI must have missed the memo. Why is an enum member a "better" choice than the more obvious "static const int foo = 10;" ?
(But I agree that either is better than a #define)
- Log in or register to post comments
TopIsn't scoped enums even better (C++11 onwards)? Should at least remove the implicit cast between enum members and int.
EDIT; for someones enjoyment: cpp.sh
:: Morten
(yes, I work for Atmel, yes, I do this in my spare time, now stop sending PMs)
- Log in or register to post comments
Top- Log in or register to post comments
TopSure... can't convert enum class to int implicitly
:: Morten
(yes, I work for Atmel, yes, I do this in my spare time, now stop sending PMs)
- Log in or register to post comments
TopWhen I asked about enums occupying memory, here is what I had in mind.
If I #define NextVal 10, then the only "memory" used is the same flash space that any numeric value would occupy. [nb: this statement is clearly true only for Harvard architectures where code occupies some nominally nonvolatile memory]
But, if I do
What is the memory "footprint"? Does is live in SRAM? Is the memory footprint any different than
If used in a place where speed is critical, aren't there usually more operations to get it out of SRAM than from FLASH (especially if it is a single byte would otherwise be embedded in the (AVR) instruction)?
And, again, folks, I am not in any way critical of the suggestions and comments above; they are really appreciated. Just trying to compare and contrast (and learn).
Jim
Jim Wagner Oregon Research Electronics, Consulting Div. Tangent, OR, USA http://www.orelectronics.net
- Log in or register to post comments
TopNone of these occupy ANY memory.
:: Morten
(yes, I work for Atmel, yes, I do this in my spare time, now stop sending PMs)
- Log in or register to post comments
TopAll of those are evaluated at compile-time?
OK, lets extend this a little. We know that
Does not, all by itself, occupy memory. Memory occupancy is determined as it is used. But, the simple variable declaration, just shown, does occupy memory once you write
And, in a Harvard architecture, that memory occupancy is SRAM rather than FLASH because MaxVal, here as a plain variable, can be altered at other points in the program. But, if I write
And use it thus:
Does MaxVal live in SRAM or does it live in FLASH (again, Harvard architecture)? Is the "assignment" made at compile time (as a #define would be) or is it assigned at run time? The same question, then, of an enum. If MaxVal had been defined as an enum, and used in an assignment statement, does that value live in SRAM or does it live in FLASH? If (and, of course, this is a big "if") speed and memory footprint are important at a given point in the program, it seems to me that this would be useful information.
HOWEVER, this thread started out about MISRA, static code analysis, and, by inference, "safety". We know that type checking is an important aspect of safety. On the other hand, safety can include constants being in FLASH where we have a very high confidence level that nothing will alter them (no buffer over-runs, no stack overflows, no nothing!). And, by "FLASH", I don't mean p-strings, but the way the AVR op-codes embeds constants into the opcodes, the results then being in FLASH.
So, please, I am not trying to be argumentative, here. Quite the contrary. Trying to learn!
Thanks for every one's input!
Jim
Jim Wagner Oregon Research Electronics, Consulting Div. Tangent, OR, USA http://www.orelectronics.net
- Log in or register to post comments
TopPerhaps some of the C experts hammer me down, but I remember it this way.
Because it's legal to make a pointer to a const, it has to live in RAM on an AVR.
add
You can't make a pointer to enum therefore it is different.
- Log in or register to post comments
TopThe case for using a name instead of a raw number is simple:
Documentation and the ease of making reliable changes.
Deciding between #define , static const int
and enum constants can be interesting.
@ka7ehk:
Unless MaxVal is global, the as-if rule allows the
compiler to do with MaxVal pretty much whatever it wants.
Even without help, the compiler will probably be
able to figure out whether MaxVal is ever changed.
If never changed, (uint8_t)10 will be quietly substituted for MaxVal.
MaxVal might be as-if-ed completely away.
Do not make a pointer to it.
x=MaxVal will probably become LDI Rx, 10 .
In C, no object may be used as the dimension of a global array.
In C++, your static const uint_t NextVal may be so used.
NextVal will almost certainly be as-if-ed away.
The necessary reasoning is required to allow its use as an array size.
Deciding between #define , static const int
and enum constants is not always interesting.
If you just want one number in the range -0x7FFF..0x7FFF
and do not need it in a constant expression,
use whatever makes you feel good.
If you need it for a constant expression, e.g. an array dimension,
in C, scratch static const int.
If you need a built-in type, scratch enum.
If you need it in assembly, use #define.
Iluvatar is the better part of Valar.
- Log in or register to post comments
TopIn the latest GNU and Microsoft C++ compilers, you can specify the size of the enums. I don't know about C compilers.
enum Events : unsigned char {
None = 0,
};
- Log in or register to post comments
TopC++ now allows one to specify the underlying type of an enumeration type.
For C, IIRC, the underlying type is always int.
Optimization usually handles size issues with enumerators.
It's not much of an issue, except for arrays of enumeration variables.
Making such arrays arrays of bytes (not enums) will sidestep the size issue.
C's enums do not help much with type safety..
ints and C's enums can be implicitly converted to each other.
Iluvatar is the better part of Valar.
- Log in or register to post comments
TopPC-lint Plus is multi-platform instead of Windows only (now: Linux 64b, macOS, Windows) along with numerous improvements.
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
Top"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopFOSS with value-added by commercial offerings.
https://github.com/SonarSource
SonarQube due to :
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopP.S.
Edit: missing URL
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopImplementing what's required per a safety standard is one of the Big 5 best practices.
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopPVS-Studio is now zero price for conditional FOSS (specific repositories, no mirrors) and conditional non-FOSS (ones as given (iow an individual) or in the specific role of student, specific comments in non-header source code files)
Free PVS-Studio for those who develops open source projects
edit: by-line
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopA zero price instance of IAR C-STAT :
IAR Embedded Workbench® for Renesas Synergy™ (Windows 7, Windows 10)
Edit: 2nd URL
"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
Top"Dare to be naïve." - Buckminster Fuller
- Log in or register to post comments
TopPages