03-15-2018 09:14 AM
Hello,
Below is the description of the problem:
TXMAIN.C:
#include <txengine.h>
double measurement;
measurement = NULL;
TXENGINE.H:
#ifndef NULL
#define NULL 0
#endif
\CVI2015\include\clang\3.3\stddef.h:
#undef NULL
#ifdef __cplusplus
# if !defined(__MINGW32__) && !defined(_MSC_VER)
# define NULL __null
# else
# define NULL 0
# endif
#else
# define NULL ((void*)0)
#endif
TXMAIN.C and TXENGINE.H is part of the project file. The NULL in TXMAIN.C file doesn't take its definition from TXENGINE.H (which is included in the project file) but takes it from STDDEF.H giving an error: assigning to 'double' from incompatible type 'void* '.
Why doesn't it take its definition from the header file included in the project file? Is there any priority change which causes it to link the constant to stddef.h instead of txengine.h.
Please help with your inputs.
Regards,
Abinaya
03-16-2018 05:05 AM
If txengine.h is a project file you should probably make the include read #include "txengine.h" instead.
And where does stddef.h get included in your sources? You do not really show the entire includes for sure.
03-16-2018 05:21 AM
Hello Rolf,
stddef.h has not been included in source file. There are other header files included but txengine.h has the value of NULL defined in it. I also noticed that if there is a statement #define ABC 1 in txengine.h and #define ABC 2 in stddef.h, the main code takes it from stddef.h only and not from txengine.h.
I also tried using #include "txengine.h" instead of <txengine.h>. That doesn't help.
Regards,
Abinaya
03-16-2018 05:33 AM - edited 03-16-2018 05:36 AM
well somewhere stddef.h gets included, probably in one of the headers you include and that header is included before your txengine.h.
stddef.h being a basic header is pretty sure to be included directly or indirectly through other headers in most LabWindows CVI header files. So if you have any includes before txengine.h they will pull in stdef.h very likely.
The use of double quotes around txengine.h was not meant to help for this particular problem but every C preprocessor has distinct behaviour for includes with double quotes compared to includes with the angle brackets. While the exact behaviour is not standardized by the C standard it is common that for double quote includes the source directory (or project file list) is searched first, while for bracket angles the system file locations are searched first).
Of course the real problem is that NULL is not meant to indicate a numeric 0 but a NULL pointer. Trying to assign NULL to an integer or floating point number should give an error, instead you should assign 0.0 to it!
03-16-2018 05:40 AM
To understand who is including stddef.h you can use Options >> Preprocess Source File menu item: as can be seenin the help:
Use the Preprocess Source File command to open a new Source window that contains preprocessed output. LabWindows/CVI replaces simple macros, expands function macros, includes header files, and resolves conditional compilation.
It's very useful in cases of doubts like yours.
03-16-2018 06:17 AM
Hi,
These are the header files included
#include <TXENGINE.H>
#include <suitelib.h>
#include <cvirte.h>
#include <userint.h>
#include <formatio.h>
#include <utility.h>
#include <ansi_c.h>
And I did use the Preprocessor source files. It began this way,
#line 1 "c:\\EPIC_MRC\\TestExec\\TXMAIN.C"
#line 1 "<built-in>"
#line 1 "<built-in>"
#line 152 "<built-in>"
#line 1 "<command line>"
#line 1 "<built-in>"
#line 1 "c:\\EPIC_MRC\\TestExec\\TXMAIN.C"
#line 35 "c:\\EPIC_MRC\\TestExec\\TXMAIN.C"
#line 1 "c:\\EPIC_MRC\\TestExec\\TXENGINE\\TXENGINE.H"
#line 248 "c:\\EPIC_MRC\\TestExec\\TXENGINE\\TXENGINE.H"
What does it refer to when it is <built-in> and <command line>?
Regards,
Abinaya
03-16-2018 06:49 AM - edited 03-16-2018 06:49 AM
Ok, situation is clear now: you #include your definition file as the first one and #define NULL there.
Next the compiler goes to ansi_c.h where the #include <stddef.h> is found: in stddef.h previous definition of NULL is discarded and a new one is placed, the one you find in your program.
You should move your include file at the end of the list and #undef previous definitions of NULL there. Or better conform with the standard definition of NULL and use some macro of yours in the program.
03-16-2018 07:01 AM
Hi Roberto,
Thanks for the explanation but the same code works fine in CVI 2010.
If we right click NULL and click "Go to definition" in CVI 2015, it refers to the definition in stddef.h while in CVI 2010 it refers to the definition in TXENGINE.H.
Regards,
Abinaya
03-16-2018 07:32 AM - edited 03-16-2018 07:32 AM
Of course! Somewhere around CVI 2012 the entire compiler backend was replaced from the NI proprietary compiler to the clang compiler system. That also came with a complete new set of standard C header files as each compiler has its own headers.
Basically your use of the NULL definition is not compatible with most modern C compilers which are much more strict in such things.
You can hack it by using the trick Roberto mentioned but better would be to not abuse the NULL definition for situations where you really want a ZERO instead.