'_WIN32_WINNT' / 'WINVER' : macro redefinition - c++

I have a VS2015 C++ project. app has to run on both Windows 7 and XP. So, I want to set _WIN32_WINNT & WINVER to _WIN32_WINNT_WINXP.
This is how stdafx.h of my project looks like:
stdafx.h
#pragma once
#include "targetver.h"
#define _WIN32_WINNT _WIN32_WINNT_WINXP
#define WINVER _WIN32_WINNT_WINXP
#include <WinSDKVer.h>
// Windows Header Files:
#include <windows.h>
When compiled, I see the following warning/error:
stdafx.h(12): error C2220: warning treated as error - no 'object' file generated
1>stdafx.h(12): warning C4005: '_WIN32_WINNT': macro redefinition
1> C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\include\SDKDDKVer.h(197): note: see previous definition of '_WIN32_WINNT'
1>stdafx.h(13): warning C4005: 'WINVER': macro redefinition
1> C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\include\SDKDDKVer.h(212): note: see previous definition of 'WINVER'

Because the #include "targetver.h" is including <sdkddkver.h> which already defines the constants _WIN32_WINNT and WINVER when they aren't already defined by the build environment.
As a matter of fact, the auto-generated targetver.h tells you exactly how to fix this:
#pragma once
// Including SDKDDKVer.h defines the highest available Windows platform.
// If you wish to build your application for a previous Windows platform, include WinSDKVer.h and
// set the _WIN32_WINNT macro to the platform you wish to support before including SDKDDKVer.h.
#include <SDKDDKVer.h>
Simple solution. Just define those constants before the inclusion of targetver.h. You might have to use the actual literal value for XP since you haven't include the header file that defines
Like this:
// x501 is XP
#define _WIN32_WINNT 0x0501
#define WINVER 0x0501
#include "targetver.h"
#include <windows.h>

Try
#include <winsdkver.h>
#undef _WIN32_WINNT
#define _WIN32_WINNT _WIN32_WINNT_WINXP
#include <SDKDDKVer.h>
You #include <winsdkver.h> so you can use _WIN32_WIN_WINXP. However, then you need to #undef _WIN32_WINNT because it is defined in <winsdkver.h>. That way when you use #define _WIN32_WINNT _WIN32_WINNT_WINXP you don't get the redefinition of _WIN32_WINNT warning.

Related

Unexpected #else

For some reason I can't explain, the compiler is outputting an error saying that it found an unexpected #else token.
This occurs at the beginning of the file :
#if defined( _USING_MFC )
#include "stdafx.h"
#else
#include <windows.h>
#endif
There is nothing before that peice of code expect several (single-line) comments.
This error occurs in a .cpp file. What you see above is the beginning of the file. There is nothing before that.
I tried adding the following code before the code defined above, and the error is now an unexpected #endif
#if 1
#include "stdafx.h"
#endif
So I suspect there is an issue with the included stdafx.h file which contains the following code :
#ifndef STDAFX_H_INCLUDED
#define STDAFX_H_INCLUDED
#include <Afx.h>
#include <Windows.h>
using namespace ATL;
#endif // STDAFX_H_INCLUDED
There's really nothing special about it. I'm also including this stdafx.h file from a stdafx.cpp file that only contains the #include statement, and it compiles correctly.
Here are the project preprocessor definitions :
_DEBUG
_WIN32_WCE=$(CEVER)
UNDER_CE
WINCE
DEBUG
_WINDOWS
$(ARCHFAM)
$(_ARCHFAM_)
_UNICODE
UNICODE
_TERMINAL_FALCONX3_CE6
_NO_CPP_EXCEPTIONS
_DONT_INCLUDE_WS_HEADERS
_USING_MFC
And some extra informations :
Compiling for Windows CE 6 using Visual Studio 2008.
What would be causing this ? Thank you.
Based on the name stdafx, I assume it is a precompiled header.
A precompiler header must be the first include (preprocessor) directive in the file, you can't put anything (not even an ifdef) before it. The only exception being a few comment lines, as those would be ignore anyway.
Based on your example, you should put the #ifdef _USING_MFC into your stdafx.h, and include Afx.h there.

Manage include order of <WinSock2.h> and <Windows.h> [duplicate]

I'm having a problem including both files.
Now, I know I need to either include Winsock2 first, then windows.h, or simply put:
#define WIN32_LEAN_AND_MEAN
but, I'm still having problems
I have a header file that is called XS.h which looks like this
#ifndef XS_H
#define XS_H
#include <winsock2.h>
#include <ws2tcpip.h>
#include <Windows.h>
#endif
and I'm including XS.h in the header Client.h.
Client.h include is looks like this :
#ifndef CLIENT_H
#define CLIENT_H
#include "XS.h"
XS.h is my only include in Client.h, yet I still get errors (and as you can see, Winsockis included before windows.h
I'm getting about 78 errors, here are some of them :
Error 90 error C3861: 'WSASetLastError': identifier not found c:\program files (x86)\windows kits\8.0\include\um\ws2tcpip.h 703
Error 61 error C2375: 'WSAStartup' : redefinition; different linkage c:\program files (x86)\windows kits\8.0\include\um\winsock2.h 2296
Error 49 error C2375: 'send' : redefinition; different linkage c:\program files (x86)\windows kits\8.0\include\um\winsock2.h 2026
How can I solve this issue?
Thanks!
Edit: I've tried to use #define _WINSOCKAPI_ as well, though it did not resolve my problems...
I have winsock.h first, then windows.h, though it still does the error for me.
Make sure that <windows.h> doesn't include <winsock.h> (which provides many of the same declarations as <winsock2.h>). In the <winsock2.h> file on my system there is this line:
#define _WINSOCKAPI_ /* Prevent inclusion of winsock.h in windows.h */
The _WINSOCKAPI_ include guard may be an internal implementation detail, but as a practical solution I would rely on it, just defining this symbol before including <windows.h>, e.g. in the compiler invocation (which for an IDE means in the IDE project settings).
Alternatively you can try to always include <winsock2.h> before <windows.h>, in order to establish the relevant include guard whatever it is (but this is I think much more fragile than just assuming that the above guard is practically well-defined);
or you can define WIN32_LEAN_AND_MEAN, which prevents <windows.h> from including <winsock.h> but also some other headers (listing from source on my system those are <cderr.h>, <dde.h>, <ddeml.h>, <dlgs.h>, <lzexpand.h>, <mmsystem.h>, <nb30.h>, <rpc.h>, <shellapi.h>, <winperf.h>, <wincrypt.h>, <winefs.h>, <winscard.h>, <winspool.h>, <ole2.h>, and <commdlg.h>). I do not recommend relying on WIN32_LEAN_AND_MEAN optimization for correctness.
I.e., minimum:
#undef UNICODE
#define UNICODE
#undef _WINSOCKAPI_
#define _WINSOCKAPI_
#include <windows.h>
#include <winsock2.h>
auto main()
-> int
{}
I made sure that an #include "Winsock2.h" is before any #include "windows.h" and "#include "Winsock.h" and this solved the case.
Just a matter of patience, look at includes one by one and establish this order, first #include "Winsock2.h" then #include "windows.h"
I checked the recursive includes, I spotted the header files which include (recursively) some #include "windows.h" and "#include "Winsock.h"and write a#include "Winsock2.h". in this files, i added#include "Winsock2.h"` as the first include.
Add the includes to pch.h:
// TODO: add headers that you want to pre-compile here
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
#include <windows.h>
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdlib.h>
#include <stdio.h>
// Need to link with Ws2_32.lib, Mswsock.lib, and Advapi32.lib
#pragma comment (lib, "Ws2_32.lib")
#pragma comment (lib, "Mswsock.lib")
#pragma comment (lib, "AdvApi32.lib")

Redefining _WIN32_WINNT while using precompiled headers

Hi I currently have a problem redefining _WIN32_WINNT even though I have
#define _WIN32_WINNT 0x0600
#define WINVER _WIN32_WINNT
in my stdafx.h it still defaults to 0x0603
I'm currently using DDSTextureLoader that came with DirectX Tutorials and by beeing 603 it uses CreateFile2 and not CreateFile which creates an error :(
Remove all the #defines in the header files, and add the preprocessor definitions -D_WIN32_WINNT=0x0600;-DWINVER=_WIN32_WINNT in the project configuration. This makes sure that the definitions take effect at the very beginning of the compiling process. For the details, see here.
If it's not appropriate to remove the #defines in the headers. You may change them to the following:
#ifndef _WIN32_WINNT
# define _WIN32_WINNT 0x0600
#endif
#ifndef WINVER
# define WINVER _WIN32_WINN
#endif

what is SDKDDKVer.h for?

All project created with MSVC have stdafx, which is precompiled headers, which I know what they are but what about targetver.h ? It includes SDKDDKVer.h, and I can't find what is that header about.
What is this for ?
targetver.h and SDKDDKVer.h are used to control what functions, constants, etc. are included into your code from the Windows headers, based on the OS that you want your program to support. I believe that targetver.h sets defaults to using the latest version of Windows unless the defines are specified elsewhere.
SDKDDKVer.h is the header file that actually defines the #defines that represent each version of Windows, IE, etc.
Line 193 of the SDKDDKVer.h (in SDK 8.1) states:
"if versions aren't already defined, default to most current"
This comment is specifically referring to the _WIN32_WINNT and NTDDI_VERSION macros.
So..
SDKDDKVer.h applies default values unless the macros have already been defined
the following code can be used to explicitly define the macros
#define _WIN32_WINNT 0x0601
#define NTDDI_VERSION 0x06010000
Interestingly enough, the SDKDDKVer.h header file has 'constant' values defined for all of the SDK versions. For example:
#define _WIN32_WINNT_WINXP 0x0501
#define _WIN32_WINNT_WIN7 0x0601
#define _WIN32_WINNT_WIN8 0x0602
One convention is to define _WIN32_WINNT and NTDDI_VERSIONin a header file called TargetVer.h, which you would reference in your pre-compiled header StdAfx.h.
#ADDTIONAL READING#
Update WINVER and _WIN32_WINNT
Using the Windows Headers
What does the Target Platform Version mean for a VS C++ project?

Boost::asio winsock and winsock 2 compatibility issue

My project uses windows.h in which winsock.h is used, and I need to include boost:assio which uses winsock2. So I get many errors that says Winsock.h already included.
I can define WIN32_LEAN_AND_MEAN. so that windows.h wouldn't use winsock. The problem is , that I need windows.h to use it, and I just need Asio for asynchronous timers. I don't need its winsock2.h . I tried searching how to disable its winsock2 use, and I found that I could do that by defining BOOST_ASIO_NO_WIN32_LEAN_AND_MEAN before including boost:asio, but I still get the same error.
#include <windows.h>
#define BOOST_ASIO_NO_WIN32_LEAN_AND_MEAN
#include <boost/asio.hpp>
Error
1>c:\program files\boost\boost_1_47\boost\asio\detail\socket_types.hpp(22): fatal error C1189: #error : WinSock.h has already been included
Try and change the order of includes. Start with boost/asio.hpp and put windows.h after it.
Usually the writers of any code library solve the compatibility issues but they can do it better if their code is the first to meet the compiler and preprocessor.
There's a similar issue with ACE, including ace/OS.h before anything else solves it.
As Danius (the OP) points out a compile with
#include <windows.h>
#include <boost/asio.hpp>
fails with this error:
1>c:\source\<SNIP>\boost\1.51.0\boost\asio\detail\socket_types.hpp(22): fatal error C1189: #error : WinSock.h has already been included
On the other hand
#include <boost/asio.hpp>
#include <windows.h>
Produces a bunch of noise and sets the windows version # incorrectly
1? Please define _WIN32_WINNT or _WIN32_WINDOWS appropriately. For example:
1> - add -D_WIN32_WINNT=0x0501 to the compiler command line; or
1> - add _WIN32_WINNT=0x0501 to your project's Preprocessor Definitions.
1> Assuming _WIN32_WINNT=0x0501 (i.e. Windows XP target).
I couldn't find any way around this that didn't leave a bad taste, but this:
#ifdef _WIN32
# ifdef USE_ASIO
// Set the proper SDK version before including boost/Asio
# include <SDKDDKVer.h>
// Note boost/ASIO includes Windows.h.
# include <boost/asio.hpp>
# else // USE_ASIO
# include <Windows.h>
# endif // USE_ASIO
#else // _WIN32
# ifdef USE_ASIO
# include <boost/asio.hpp>
# endif // USE_ASIO
#endif //_WIN32
Does produce a clean compile.
<EDITORIAL> It shouldn't be that hard </EDITORIAL>
For me, switching the order of includes caused compile errors with another Microsoft include I was using - that was declaring things with "typedef interface".
Since my error was coming from socket_types.h, from these lines:
# if defined(_WINSOCKAPI_) && !defined(_WINSOCK2API_)
# error WinSock.h has already been included
# endif // defined(_WINSOCKAPI_) && !defined(_WINSOCK2API_)
I put an include of "winsock2.h" before the Windows.h, and then finally the boost/asio.hpp include, and things then compiled happily.
#ifdef BOOST_OS_WINDOWS
#define _WIN32_WINNT 0x0501
#if _WIN32_WINNT <= 0x0501
#define BOOST_ASIO_DISABLE_IOCP
#define BOOST_ASIO_ENABLE_CANCELIO
#endif
#endif
An other workarround I used is to concentrate all asio dependent
code in an XXX.hpp file and include it on the top of each windows implementing
XXX.cpp file where you use its objects.
this method place the include asio above any other include windows.h and work arround the problem.