Hello,
I am trying to compile a project for STM32F103CB, but it doesn't seem to work properly. First of all, this project compiles and runs on IAR SDK. I ported it on uVision 5 SDK, and, after quite some pain, I made it compile. The problem is, I am still getting this warning:
Libraries\X_Lib\src\X_Configuration.c(438): warning: #223-D: function "roundf" declared implicitly GAverage[0] = (u32)(roundf((float)GAverage[0]/(float)(GSampleCount)));
although I am including the math.h file in X_Configuration.c:
#include <math.h>
in math.h, roundf is defined as
extern _ARMABI_FPEXCEPT double round(double /*x*/); extern _ARMABI_FPEXCEPT float roundf(float /*x*/); _ARMDEFLD1(round);
...what am I doing wrong? Is there some precise setting I overlooked?
Thanks a lot for your time!
You probably need to instruct the compiler to include the proper library. On GCC that is achieved using -lm linker option.
How to do that? Because it looks like it finds the <math.h> include. In fact, it lists it under the dependencies of X_configuration.c, and it does not generate file-not-found error. In addition, I added all the necessary libs under C/C++ include path, and the compiler string shows -l C:\Keil\ARM, which is where the standard C library is supposed to be (well in a subfolder).
I am stuck.
Ahem, no. That's no definition; it's a declaration. You really need be perfectly clear about that distinction.
And are you sure that the compiler actually sees that line you're looking at? I.e. it's not disabled by some #if clause surrounding it, or by you looking at a completely different copy of <math.h> than the one the compiler is actually using?
It's often necessary to generate and double-check the preprocessor's intermediate version of your source to figure out such puzzles.
Hans, thank you! That was the trick.
Ahem, no. That's no definition; it's a declaration. You really need be perfectly clear about that distinction. --- yes sorry, I am a bit rusty with the nomenclature but I do have in mind the difference.
And are you sure that the compiler actually sees that line you're looking at? I.e. it's not disabled by some #if clause surrounding it, --- yep! That was the case, I didn't think about that. It was surrounded by
#ifdef __USE_C99_MATH
so I just had to add
#define __USE_C99_MATH
to my X_configuration.c file
or by you looking at a completely different copy of <math.h> than the one the compiler is actually using? --- no, I was looking at the file that was automatically listed under X_configuration.c
It's often necessary to generate and double-check the preprocessor's intermediate version of your source to figure out such puzzles. --- yes - me lazy :P - I didn't think about going through the whole math.h file.
Thanks a lot to both of you for your help :)!
I have to advise caution and some further checking before you consider that your final solution. Macros like that (in implementation name space, as per the two leading '_') shouldn't really be set by application code unless the tool's or library's documentation explicitly says that's what you should do. In short, they're not yours to #define. There's probably some global compiler switch you're supposed to use instead, which will set this switch in turn.
Hans,
indeed. In fact, there is an option in Project -> Options for target ... -> C/C++ tab to define/undefine Preprocessor Symbols. It's in the same tab in which you add the include paths for your project.
Thank you again for this detail. :)
indeed. In fact, there is an option in Project -> Options for target ... -> C/C++ tab to define/undefine Preprocessor Symbols.
I'm afraid you missed my point. The problem is not about where you make that #define, whether in source or in the compiler flags. It's about whether you're allowed to #define that macro at all. If you're not, you might break a lot more than you fixed.
Now, the official definition of the C programming language says you're not allowed to do this, because names starting on a double underscore are reserved to the language's implementors (e.g.: Keil or IAR). So you would need some other instance to give you this permission, thus overriding the language standard. The only applicable candidate to be that instance is the documentation of the compiler or library you found this in. So please: look it up.