Adding a Windows Form at a new C++ project [duplicate] - c++

This question already has answers here:
How do I create a C++/CLI Winforms app in VS2012?
(2 answers)
Closed 8 years ago.
Okay so I am just beginning to learn C++ and I would like to do so using Windows Forms. I created a Blank project and tried to add a form. I get this error.
Error 2 error LNK1120: 1 unresolved externals C:\Users\Ryan\Google Drive\C++\Hello C++\Debug\Hello C++.exe 1 1 Hello C++
&&
Error 1 error LNK2001: unresolved external symbol _main C:\Users\Ryan\Google Drive\C++\Hello C++\Hello C++\LINK Hello C++
I have set my Startup to main and set SubSystem to Windows (/SUBSYSTEM:WINDOWS)
My Project is called Hello C++ and my form is called MyForm.
Any help?
Cheers

You're adding Windows Forms (which are forms for C# or VB.NET) to a C++ project.
This is not gonna work: C++ is an unmanaged language while you're adding a form for a managed language.
Put it simply: Windows Forms are usable if you choose "C#" or "Visual Basic .NET" as a VS project.

In addition to the "Forms" problem, setting /SUBSYSTEM:WINDOWS means your program is required to have a winmain entry point, not main. That is probably the reason for the error. (You did not show us the complete error message.)
To use Forms change languages to C#. To build a GUI in C++ you can use a Win32 app, or MFC, or ATL, or Qt.

Well the entry point should be
int CALLBACK WinMain(
_In_ HINSTANCE hInstance,
_In_ HINSTANCE hPrevInstance,
_In_ LPSTR lpCmdLine,
_In_ int nCmdShow
);
and not the usual "main". There is good reason for that and you can read about it here: http://msdn.microsoft.com/en-us/library/windows/desktop/ms633559(v=vs.85).aspx

Related

C++ windows code links in 64bit but not in 32bit

I have code written in C++ on windows.
My code compiles and links when I compile it as x64 but not when I change the build configuration to x86.
The failure is a linking error.
I'm using the function RtlIsNameInExpression from ntdll.
When I compile it in 32bit mode I get a linkage error (LNK2019) of unresolved external.
Any ideas why this might happen?
10x
first of all - how you declare function and which symbol can not found linker ?
declaration must be
extern "C" NTSYSAPI BOOLEAN NTAPI RtlIsNameInExpression(
_In_ PCUNICODE_STRING Expression,
_In_ PCUNICODE_STRING Name,
_In_ BOOLEAN IgnoreCase,
_In_opt_ PWCH UpcaseTable
);
i can guess that you miss NTAPI i.e __stdacall keyword if you copy-paste from here. for x64 exist only one calling convention, but for x86 exist different between __stdcall and __cdecl for example. this can explain why this found in x64 but not found in x86
what error give you linker (not compiler !) ? unresolved external symbol __imp__RtlIsNameInExpression ? (if yes you really forget __stdcall set) or __imp__RtlIsNameInExpression#16 ? in this case you declare function correct, but your ntdll.lib not containing this symbol. (may be you use old ntdll.lib
for xp ? ) simply search __imp__RtlIsNameInExpression#16 string as is in ntdll[p].lib - are it found ? if not you have old (xp) version of ntdll i guess.
The answer is in the online documentation for that function:
This function has no associated header file. The associated import library, Ntdll.lib, is available in the Microsoft Windows Driver Kit (WDK). You can also call this function using the LoadLibrary and GetProcAddress functions to dynamically link to Ntdll.dll.
If you can't add the ntdll.lib file from the WDK to your link command, then you need to use the LoadLibrary-GetProcAddress approach.
Also from the same section of documentation:
The functions and structures in Winternl.h are internal to the operating system and subject to change from one release of Windows to the next, and possibly even between service packs for each release. To maintain the compatibility of your application, you should use the equivalent public functions instead. Further information is available in the header file, Winternl.h, and the documentation for each function.

C++ & VS2015: Problems with unresolved externals and namespaces (maybe caused by openCV) [duplicate]

This question already has answers here:
What is an undefined reference/unresolved external symbol error and how do I fix it?
(39 answers)
Closed 6 years ago.
Hello fellow community,
I am really new to stackoverflow although I often find great and inspiring answers, when I am really stucked. This one I wasn't able to find anything, so I post it.
Short introduction: I teached myself c++ in 2010 and then changed to VB, C# and Java. I completely missed this whole managed system and was really confused, when things didn't work like they used to.
The problem: My application is using openCV and I already managed to have working builds. At the moment I try to show a picture in a windows forms picturbox and at the same time manipulating it with openCV.
include structure (general):
main.cpp includes
main.h
main.h includes
openCV
string
msclr/marshal_cppstd.h
form1, form2, form3
the probelm ocurrs in form3.h. Basic structure of form3.h:
#pragma once
cv::Mat srcImg;
HBITMAP get_srcImg()
{
HBITMAP b = CreateBitmap(srcImg.cols, srcImg.rows, 1, 32, srcImg.data);
return b;
}
namespace ownProject{//this is all automatically generated by the designer
class form {...}
I get:
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol "extern "C" struct HBITMAP__
* cdecl CreateBitmap(int,int,unsigned int,unsigned int,void const *)" (?CreateBitmap##$$J0YAPEAUHBITMAP##HHIIPEBX#Z) referenced in function "struct HBITMAP__ * cdecl get_srcImg(void)"
(?get_srcImg##$$FYAPEAUHBITMAP##XZ) Path_recognition
And I don't know how to solve it. If I delete the createBitmap function, everything is working properly. The problem is I need to convert the picture between the pictureBox and openCV-functions. I had unresolved externals before and fixed it by adjusting the include hierarchy and deleting all cpp-files except main.cpp.
I hope you can help me. Thank you.
You should link to Gdi32.lib
#pragma comment(lib, "Gdi32.lib")
That should solve your problem

LNK2019 and LNK1120

I am currently facing a problem which is as the error below
Error 1 error LNK2019: unresolved external symbol _main referenced in function ___tmainCRTStartup MSVCRTD.lib assignment
I am trying to redo the program, I have follow the step to do as same as article post by any user. I try to change the character set to not set, still no function available. I try to change from console to win turn out _winmain#16 error, and I change back _main error
I ald recreate the whole solution file i didnt recreate the coding or .CPP and .H file in my C++ programming,
How do I solve it, I already research for 3 - 4 days, but I still unable to get the answer that I have expect. Hopefully this may help me to complete the program. Thank you and your help much appreciated.
You've probably got some incompatible settings in your solution. In Visual Studio 2010, Create a new project, and select Win32 Console Application from the templates list. Click Next on the Wizard page, and select Console Application, and Empty Project, then Finish. Create a new .cpp file and put this code into it
int main ()
{
}
This should compile and link.
if it is an windows program:
1.menu-Project->Properties, to open this "Property Pages" window
2.then choose Configuration Properties->C/C++->Preprocessor,and delete "_CONSOLE" in Preprocessor Definitions , add "_WINDOWS".
3.return the first step:Configuration Properties->Linker->System,change it to Windows(/SUBSYSTEM:WINDOWS) in SubSystem
if it it a console program:
1.menu--> Project->Properties, pop out the "Property Pages" window
2.then choose Configuration Properties->C/C++->Preprocessor,and delete "_WINDOWS" int Preprocessor Definitions add "_CONSOLE".
3.return the first step:Configuration Properties->Linker->System,change it to CONSOLE(/SUBSYSTEM:CONSOLE) in SubSystem
Do you have a main function in your program? Because the windows runtime library (The MSVCRTD.lib you mentioned) will call your main function as the entry point. If you don't have one, there is a link error.
WinMan is the entry point for the win32 program.

LNK2019 unresolved external symbol NtOpenFile

I am facing linker error with my code. I am trying to compile with Visual Studio command Prompt (2010) in Win-7 X64 bit m/c.
The error which i see are as below.
dust2.obj
dust2.obj : error LNK2019: unresolved external symbol _NtOpenFile#24 referenced
in function _main
dust2.obj : error LNK2019: unresolved external symbol _RtlAnsiStringToUnicodeStr
ing#12 referenced in function _main
dust2.obj : error LNK2019: unresolved external symbol _RtlInitAnsiString#8 refer
enced in function _main
dust2.exe : fatal error LNK1120: 3 unresolved externals
The simplified version of my code is like this:
#include <windows.h>
#include <iostream>
#include <Winternl.h>
using namespace std;
int main()
{
NTSTATUS Status;
OBJECT_ATTRIBUTES Obja;
HANDLE SourceFile;
PUNICODE_STRING PathName=0;
PANSI_STRING p_path=0;
const char* ccp_path = "D:\\txt.txt";
RtlInitAnsiString( p_path,ccp_path );
RtlAnsiStringToUnicodeString( PathName, p_path, true );
IO_STATUS_BLOCK IoStatusBlock;
wprintf(L"%s", PathName->Buffer);
InitializeObjectAttributes(
&Obja,
PathName,
OBJ_CASE_INSENSITIVE,
NULL,
NULL
);
Status = NtOpenFile(
&SourceFile,
FILE_LIST_DIRECTORY | FILE_READ_EA | FILE_READ_ATTRIBUTES,
&Obja,
&IoStatusBlock,
FILE_SHARE_READ | FILE_SHARE_WRITE,
FILE_DIRECTORY_FILE | FILE_OPEN_FOR_BACKUP_INTENT | FILE_OPEN_REPARSE_POINT
);
if(SourceFile == INVALID_HANDLE_VALUE){
printf("\nError: Could not open file\n");
return 0;
}
cout<<endl<<endl;
system("pause");
return 0;
}
In another post in this forum the solution of these kind of problem was mention to include a #pragma.
I tried this solution by adding #pragma like this
#pragma comment(lib, "ntdll")
but on compilation i see another error that says "LINK : fatal error LNK1104: cannot open file 'ntdll.lib'".
I will much appreciate your help to resolve this problem. Thanks..
Can't let this question go unanswered like this. Because although the remark by Mladen is largely right for this particular native API, the whole topic deserves an in-depth discussion.
Preliminary cautionary note
Up front I should note that in many many cases it is neither desirable nor necessary to use one of the native API functions on Windows. However, there are a few cases where the Win32 API doesn't provide the means to query information or even manipulate data and so on. One such case would be several of the information classes available for NtQueryInformationFile/ZwQueryInformationFile.
One good example is the enumeration of alternate data streams on files and directories, which can be done using the Win32 API, in particular by using the backup APIs, but will require special privileges in that case. Not so if you resort to the native API. The same used to be true for hard links until Windows 2000, which introduced CreateHardLink to the Win32 API. Although in this particular case if you knew your way around you could have used MoveFileEx with MOVEFILE_CREATE_HARDLINK ever since it got introduced (although Microsoft still as of this writing marks it as Reserved for future use ... meh).
The canonical books about the native API are these two:
Windows NT/2000 Native API Reference, Gary Nebbett
Undocumented Windows 2000 Secrets: A Programmer's Cookbook, Sven B. Schreiber (free version from the author's website here)
... there are more, including one that discusses NT 4 and preceded Nebbett's book. But Nebbett's book used to start the hype around the native API, much like Hoglund's book started the hype around Windows rootkits. Not a reference regarding the Native API topic but still good:
Windows Internals, Mark Russinovich et. al.
Check out this website for a huge number of native API functions "documented":
http://undocumented.ntinternals.net/
So remember: the inherent risk when using these functions is that they go away in a future Windows version or their semantics change without prior notice. So be careful when you use them, if you use them.
On to glory ...
How to call native API functions
Actually there are two ways to call these functions. Microsoft was forced to disclose some of the native API functions in one of the antitrust law suits some years ago. These were shoved into winternl.h of the SDK. Microsoft expresses it thus:
The NtOpenFile documentation is provided for the sake of full API
coverage. NtOpenFile is equivalent to the ZwOpenFile function
documented in the DDK. For more information on the ZwOpenFile and
related functions, go to http://msdn.microsoft.com/library. In the
left-hand pane, click Windows Development, then click Driver
Development Kit.
However, there is no accompanying ntdll.lib file in the SDK. Microsoft suggests you link those functions dynamically (second option below).
You have several options:
The most common is to do as you did. But the ntdll.lib import library is only part of the WDKs, not the DDKs.
Use GetProcAddress to find the function pointer and call it. GetModuleHandle is sufficient for the Win32 subsystem since every Win32 program is guaranteed to have loaded ntdll.dll.
Method 1: ntdll.lib
If you have the DDK/WDK - for Driver Development Kit and Windows Driver Kit respectively - you get a full set of ntdll.lib files already. On my system (Windows 7 WDK 7600.16385.1):
C:\WINDDK\7600.16385.1\lib\win7\amd64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\win7\i386\ntdll.lib
C:\WINDDK\7600.16385.1\lib\win7\ia64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wlh\amd64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wlh\i386\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wlh\ia64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wnet\amd64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wnet\i386\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wnet\ia64\ntdll.lib
C:\WINDDK\7600.16385.1\lib\wxp\i386\ntdll.lib
Create your own makeshift ntdll.lib
Otherwise you have to generate ntdll.lib yourself from the output of dumpbin (or by other means that allow to parse the exports of the DLL) which you can then output into a module definition file from which you can build an export .lib. Sounds convoluted? Not so much, let's see ;)
Using Ero Carrera's pefile Python module, we can do this:
import os, re, sys
from os.path import basename, dirname, join, realpath
try:
import pefile
except ImportError:
try:
sys.path.append(join(realpath(dirname(__file__)), "pefile"))
import pefile
except:
raise
def main(pename):
from pefile import PE
print "Parsing %s" % pename
pe = PE(pename)
if not getattr(pe, "DIRECTORY_ENTRY_EXPORT", None):
return "ERROR: given file has no exports."
modname = basename(pename)
libname = re.sub(r"(?i)^.*?([^\\/]+)\.(?:dll|exe|sys|ocx)$", r"\1.lib", modname)
defname = libname.replace(".lib", ".def")
print "Writing module definition file %s for %s" % (defname, modname)
with open(defname, "w") as f: # want it to throw, no sophisticated error handling here
print >>f, "LIBRARY %s\n" % (modname)
print >>f, "EXPORTS"
numexp = 0
for exp in [x for x in pe.DIRECTORY_ENTRY_EXPORT.symbols if x.name]:
numexp += 1
print >>f, "\t%s" % (exp.name)
print "Wrote %s with %d exports" % (defname, numexp)
print "\n\nUse this to create the export lib:\n\tlib /def:%s /out:%s" % (defname, libname)
if __name__ == '__main__':
if len(sys.argv) != 2:
sys.exit("ERROR:\n\tSyntax: fakelib <dllfile>\n")
sys.exit(main(sys.argv[1]))
A sample output of running this script (when named fakelib.py) would be:
> fakelib.py ntdll.dll
Parsing ntdll.dll
Writing module definition file ntdll.def for ntdll.dll
Wrote ntdll.def with 1984 exports
Use this to create the export lib:
lib /def:ntdll.def /out:ntdll.lib
Then we run the command as given on the last line. It is even better to give the /machine: parameter, of course. This is left as an "exercise" (*cough* *cough*) to the reader. The output with VS 2012 will be:
> lib /def:ntdll.def /out:ntdll.lib
Microsoft (R) Library Manager Version 11.00.51106.1
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : warning LNK4068: /MACHINE not specified; defaulting to X86
Creating library ntdll.lib and object ntdll.exp
Congratulations. You can now use the ntdll.lib created by Microsoft's own lib.exe to statically import from ntdll.dll, even without having the "real" (original) .lib on your system.
Adjust the path and file names to your needs and tastes.
When using MinGW
Damon pointed out in a comment that the toolchain included with MinGW contains a tool gendef that can do the job of above Python script and that the output can be fed to dlltool.
Issues
The above method works perfectly when targeting x64 (64-bit), but for x86 (32-bit) I have encountered linker errors at times.
The issue is that the name decoration for __stdcall differs between x64 and x86. The former doesn't really use the same __stdcall as x86 and therefore just prepends an underscore. However, the latter also appends a the number of arguments times sizeof(void*) (i.e. 4). So for one argument the decorated function name for a function int __stdcall foo(int); becomes _foo#4.
This KB article from Microsoft outlines a way to get around the issue.
Method 2: dynamically imported, using GetProcAddress
Documentation in MSDN states (for NtOpenFile):
Note that the DDK header file Ntdef.h is necessary for many constant
definitions as well as the InitializeObjectAttributes macro. The
associated import library, Ntdll.lib is also available in the DDK. You
can also use the LoadLibrary and GetProcAddress functions to
dynamically link to Ntdll.dll.
Declare a function type, e.g. here we declare the type TFNNtOpenFile suitable in your case:
typedef NTSTATUS (NTAPI *TFNNtOpenFile)(
OUT PHANDLE FileHandle,
IN ACCESS_MASK DesiredAccess,
IN POBJECT_ATTRIBUTES ObjectAttributes,
OUT PIO_STATUS_BLOCK IoStatusBlock,
IN ULONG ShareAccess,
IN ULONG OpenOptions
);
... and then retrieve the function pointer and call it:
TFNNtOpenFile pfnNtOpenFile = (TFNNtOpenFile)GetProcAddress(GetModuleHandle("ntdll.dll"), "NtOpenFile");
status = pfnNtOpenFile(...); // can't be bothered to type out all parameters ;)
an alternative way of retrieving the function pointer could be this one:
static NTSTATUS (NTAPI *NtOpenFile)(
OUT PHANDLE,
IN ACCESS_MASK,
IN POBJECT_ATTRIBUTES,
OUT PIO_STATUS_BLOCK,
IN ULONG,
IN ULONG
);
(FARPROC)&NtOpenFile = GetProcAddress(GetModuleHandle("ntdll.dll"), "NtOpenFile");
which could be condensed even further by using the preprocessor stringification operator (#). The choice is yours.
These functions cannot be called directly because they belong to internal API and are not exposed through any of the libraries. You need to obtain addresses of these function using GetProcAddress.
For more information look here.

Removing console window for Glut/FreeGlut/GLFW?

Under Visual C++, I have played around with Glut/FreeGlut/GLFW. It seems that everyone of these projects adds a CMD window by default. I tried removing it going under:
Properties->C/C++->Preprocessor->Preprocessor
Definitions
From here, I remove the _CONSOLE and replace it with _WINDOWS
Then I went under:
Properties->Linker->System->SubSystem
And I set the option to Windows (/SUBSYSTEM:WINDOWS)
Then when I try compiling under GLFW, I get the following building errors:
Error 1 error LNK2001: unresolved
external symbol _WinMain#16
MSVCRT.lib
Error 2 fatal error LNK1120: 1
unresolved externals glfwWindow.exe
Is it possible to remove the console window?
Under the linker options, set your entry point to mainCRTStartup . This function does the necessary setup of the MS libc and then calls main.
Most linkers support options that automatically remove the console startup code.
I think on GCC it's called -mwindows
My project just has a main, (no WinMain) and to disable console, I just set Linker->System->SubSystem to "Windows (/SUBSYSTEM:WINDOWS)" instead of "Console (/SUBSYSTEM:CONSOLE)" and the console goes away.
You don't need to mess with the Preprocessor Definitions to remove the console window.
I know my answer is a few years late, but I hope it helps.
To get rid of the console using cmake, the link flags can be set as follows:
set_target_properties(exe_name PROPERTIES
LINK_FLAGS "/ENTRY:mainCRTStartup /SUBSYSTEM:WINDOWS")
Non-console Windows applications use the WinMain() entry point convention. Your Glut examples probably use the standard C main() convention.
If you want a quick fix just for the demo app, the WinAPI function FreeConsole() might help.
MSDN: http://msdn.microsoft.com/en-us/library/ms683150(v=vs.85).aspx
You need to write a WinMain entry point and copy your existing code (from main):
int CALLBACK WinMain(
__in HINSTANCE hInstance,
__in HINSTANCE hPrevInstance,
__in LPSTR lpCmdLine,
__in int nCmdShow
){
// ...
}
If you create a new project as a console application, it will always run as such. You have to create a new GUI project if you want to run it in an actual window, otherwise the correct headers and libraries will not be included.
Also the WinMain function that's required will be included for you in the resulting template files.
When I've gotten an error like that I was able to fix it by entering that following text in the linker, section Advance, option Entry Point the following:
main