Renaming a C++ thread when running under Visual Studio 2010 extension package - c++

I'm using the following code (from MSDN) to rename a C++ thread:
#include <windows.h>
const DWORD MS_VC_EXCEPTION=0x406D1388;
#pragma pack(push,8)
typedef struct tagTHREADNAME_INFO
{
DWORD dwType; // Must be 0x1000.
LPCSTR szName; // Pointer to name (in user addr space).
DWORD dwThreadID; // Thread ID (-1=caller thread).
DWORD dwFlags; // Reserved for future use, must be zero.
} THREADNAME_INFO;
#pragma pack(pop)
void SetThreadName( DWORD dwThreadID, char* threadName)
{
THREADNAME_INFO info;
info.dwType = 0x1000;
info.szName = threadName;
info.dwThreadID = dwThreadID;
info.dwFlags = 0;
__try
{
RaiseException( MS_VC_EXCEPTION, 0, sizeof(info)/sizeof(ULONG_PTR), (ULONG_PTR*)&info );
}
__except(EXCEPTION_EXECUTE_HANDLER)
{
}
}
And it is working great overall. However, when trying to execute this code in Visual Studio (2010) extension package, I get the following unhanded exception and the name of the thread doesn't change:
System.Runtime.InteropServices.SEHException occurred
Message: External component has thrown an exception.
Anyone has any clue what's going on there? I realize there might be some issues with changing a thread that way from extensions, however, it is undocumented and it seems to be working fine from a standard add-in.
Thanks!

I'm not certain whether this is the cause of your problem but according to this MSDN documentation the SetThreadName function only applies to native code. Judging from the exception you're seeing you're compiling with the /clr option so you should probably use the managed code equivalent of this. Follow the link under the See Also section in the first link, it shows the snippet to use for managed code.
HTH,
Ashish.

Sounds familiar. Here's what the insides of our SetThreadName looks like (in a mixed native C++, C++/CLI, C# app):
#pragma warning(disable: 6312 6322)
__try
{
RaiseException( 0x406D1388, 0, sizeof(info) / sizeof(DWORD), (DWORD*)&info );
}
// don't implement MSDN's suggested fix for 6312 here - it causes a nasty unhandled exception
// to bubble up into managed code. Disable the compiler warning instead.
__except(EXCEPTION_CONTINUE_EXECUTION)
{
}
#pragma warning(default: 6312 6322)

Related

MS Detours - DetourAttach fails

Feeling stupid here but why is this code giving me a syntax error in Visual
Studio when trying to compile it?
DetourAttach(&(PVOID&)true_create_file, create_file);
The compiler complains with (underlining the & after PVOID)
Error (active) E0018 expected a ')'
The code is literally copied from the Detours example page. I'm assuming it is because my containing file has a .c extension and is thus compiled as C by VS while the example has a .cpp extension and is compiled as C++.
I'm not entirely sure what's going on in this line with all the casting. Why doesn't the C compiler like it and how do I get it to compile this line?
Here's the complete listing of the code:
#include <Windows.h>
#include "detours.h"
#pragma comment(lib, "detours.lib")
static HANDLE(WINAPI *true_create_file) (LPCSTR file, DWORD access,
DWORD share, LPSECURITY_ATTRIBUTES sec, DWORD disp, DWORD flags,
HANDLE tmpl) = CreateFileA;
HANDLE WINAPI create_file(LPCSTR file, DWORD access, DWORD share,
LPSECURITY_ATTRIBUTES sec, DWORD disp, DWORD flags, HANDLE tmpl) {
}
int hook_create_file() {
DetourTransactionBegin();
DetourUpdateThread(GetCurrentThread());
/* syntax error */
DetourAttach(&(PVOID&)true_create_file, create_file);
DetourTransactionCommit();
}
PVOID is defined as
typedef void *PVOID;
The &(PVOID&) part: cast the parameter to a reference to a pointer to void first, and then taking the address of that. As comment point out, you compile it as C, but the reference operation do not exist in C. So the compiler recognizes "&" as taking address, but only ")" behind it, then get the expected a ')' error.
Since PVOID& doesn't make sense here, just to increase readability. You could use PVOIDinstead of PVOID& here:
DetourAttach(&(PVOID)true_create_file, create_file);
You could also get the DetourAttach function details from here.

Unresolved external symbol CLRCreateInstance

I wrote some native C++ code with the help of the Internet that loads the .NET Runtime and invokes a method that has the signature: public static int MethodNameHere(String pwzArgument) from a class in a managed assembly.
However, I can't seem to compile the code using Visual Studio into a native DLL (64-bit), because there seems to be a linking issue with CLRCreateInstance(), even though I am including "MetaHost.h" in the .cpp source file.
Here is the entire code:
#include "MetaHost.h"
extern "C" {
__declspec(dllexport) DWORD __stdcall CallManagedMethod(LPCWSTR managedDLLPath, LPCWSTR classPathInAssembly, LPCWSTR methodName, LPCWSTR parameter) {
// Bind to the CLR runtime..
ICLRMetaHost* pMetaHost = nullptr;
CLRCreateInstance(CLSID_CLRMetaHost, IID_ICLRMetaHost, (LPVOID*) &pMetaHost);
ICLRRuntimeInfo* pRuntimeInfo = nullptr;
pMetaHost->GetRuntime(L"v4.0.30319", IID_ICLRRuntimeInfo, (LPVOID*) &pRuntimeInfo);
ICLRRuntimeHost* pClrRuntimeHost = nullptr;
pRuntimeInfo->GetInterface(CLSID_CLRRuntimeHost, IID_ICLRRuntimeHost, (LPVOID*) &pClrRuntimeHost);
pClrRuntimeHost->Start();
// Okay, the CLR is up and running in this (previously native) process.
// Now call a method on our managed C# class library.
DWORD dwRet = 0;
pClrRuntimeHost->ExecuteInDefaultAppDomain(managedDLLPath, classPathInAssembly, methodName, parameter, &dwRet);
// Don't forget to clean up.
pClrRuntimeHost->Release();
pRuntimeInfo->Release();
pMetaHost->Release();
return dwRet;
}
}
Any help?
A .h file does not solve a linking problem, it merely adds them. The MSDN article you linked to fumbles the usual way that include and link hints are documented, "Included as a resource" is quite unhelpful. In C++ you have to link mscoree.lib to get the symbol resolved. It is the import library for mscoree.dll and included in the SDK.
Simplest way is to add #pragma comment(lib, "mscoree.lib") after your #include.

Find where a thread started in Visual Studio 2010 C++

So I'm supposed to fix a dead-lock without profiler (at least I didn't find any useful one) in an application that runs unbeliavable 283 threads according to VisualStudio. Most of the threads are called Thread _threadstartexThread _threadstartex, making it hard to see what they belong to.
Therefore I decided that my first step is going to find where the threads were started and set some names for them, so I can distinguish boost and Qt internal threads and our application threads.
The question therefore is (in case someone forgot the title): How to find FILE and LINE NUMBER where thread seen in visual studio was started?
Years, years ago I once learned at Microsoft TechEd that you can set a thread name when Visual Studio is your debugger. The code to call in your program is:
typedef struct tagTHREADNAME_INFO
{
DWORD dwType; // must be 0x1000
LPCSTR szName; // pointer to name (in user addr space), UTF-8
DWORD dwThreadID; // thread ID (-1=caller thread)
DWORD dwFlags; // reserved for future use, must be zero
} THREADNAME_INFO;
void SetThreadName(DWORD dwThreadID, LPCSTR szThreadName)
{
THREADNAME_INFO info;
info.dwType = 0x1000;
info.szName = szThreadName;
info.dwThreadID = dwThreadID;
info.dwFlags = 0;
#pragma warning(push)
#pragma warning(disable: 6312) // Possible infinite loop: use of the constant EXCEPTION_CONTINUE_EXECUTION in the exception-filter expression of a try-except. Execution restarts in the protected block
#pragma warning(disable: 6322) // Empty _except block
__try {
RaiseException(0x406D1388, 0, sizeof(info) / sizeof(ULONG_PTR), (ULONG_PTR*)&info);
}
__except (EXCEPTION_CONTINUE_EXECUTION) {
}
#pragma warning(pop)
}
References: MSDN How to: Set a Thread Name in Native Code and How to: Set a Thread Name in Managed Code.
Maybe Visual Studio 2015 has some better debugging facilities that may help you? Microsoft has implemented a lot of enhancements, but I am not sure of one of them will help you with your problem.

Is it OK to Edit GCC Header Files?

I was trying to compile some example code from MSDN with GCC on Windows 7 (please ignore the use of goto and the terrible formatting; it's not my code):
#include <stdio.h>
#include <windows.h>
typedef struct _TOKEN_ELEVATION {
DWORD TokenIsElevated;
} TOKEN_ELEVATION, *PTOKEN_ELEVATION;
BOOL IsProcessElevated()
{
BOOL fIsElevated = FALSE;
DWORD dwError = ERROR_SUCCESS;
HANDLE hToken = NULL;
if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken))
{
dwError = GetLastError();
goto Cleanup;
}
TOKEN_ELEVATION elevation;
DWORD dwSize;
if (!GetTokenInformation(hToken, TokenElevation, &elevation,
sizeof(elevation), &dwSize))
{
dwError = GetLastError();
goto Cleanup;
}
fIsElevated = elevation.TokenIsElevated;
Cleanup:
if (hToken)
{
CloseHandle(hToken);
hToken = NULL;
}
if (ERROR_SUCCESS != dwError)
{
throw dwError;
}
return fIsElevated;
}
int main()
{
try
{
if (IsProcessElevated())
wprintf (L"Process is elevated\n");
else
wprintf (L"Process is not elevated\n");
}
catch (DWORD dwError)
{
wprintf(L"IsProcessElevated failed w/err %lu\n", dwError);
}
}
I kept getting the error TokenElevation was not declared in this scope. While trying to figure it out I saw that the TokenElevation member of the TOKEN_INFORMATION_CLASS struct was between two #ifdef tags:
typedef enum _TOKEN_INFORMATION_CLASS {
TokenUser=1,
TokenGroups,
TokenPrivileges,
TokenOwner,
TokenPrimaryGroup,
TokenDefaultDacl,
TokenSource,
TokenType,
TokenImpersonationLevel,
TokenStatistics,
TokenRestrictedSids,
TokenSessionId,
TokenGroupsAndPrivileges,
TokenSessionReference,
TokenSandBoxInert,
TokenAuditPolicy,
TokenOrigin,
//#if (_WIN32_WINNT >= 0x0600)
TokenElevationType,
TokenLinkedToken,
TokenElevation,
TokenHasRestrictions,
TokenAccessInformation,
TokenVirtualizationAllowed,
TokenVirtualizationEnabled,
TokenIntegrityLevel,
TokenUIAccess,
TokenMandatoryPolicy,
TokenLogonSid,
//#endif
MaxTokenInfoClass
} TOKEN_INFORMATION_CLASS;
I commented these out and the code compiled without errors or warnings. My question is really two questions. Is their a better way to do this (define something in my code?) and, in the long run, will editing header files hurt me?
Editing the headers will hurt because your code is no longer being built against an external library you simply depend on. Instead you have effectively made that external code part of your project, and now you have to manage it like other source code in your project. You should keep it in your version control system, for example.
Yes, there is a better way: you can simply define _WIN32_WINNT as the Windows code expects it to be defined. Visual Studio projects define this macro by default, but you have to do that manually when building with gcc on Windows.
This page defines the values for each version of Windows.
Yes, you can edit and change GCC header files.
Be aware that when GCC upgrades, your changes may be lost. You would have to merge your changes into the newer header files.
For this reason, common rule of thumb is not to modify compiler header files.
Edit 1:
Also, if you share your code, you will need to have the clients make the same mods to the GCC header files that you did. Some clients may not want their compiler header files changed. Same rules apply when you have other people working on the same project.
Also, will your changes affect future projects? Future projects may use the GCC header files also.
You can modify them but it is usually a bad idea, because it will make you compilation difficult to repeat.
In this particular case, the right solution is just to define _WIN32_WINNT as 0x0600 or higher. This macro is used to specify the Windows version you are targeting, and you clearly are targeting at least version 6, or you would not be able to use this value. The Windows SDK header files use this macro to conditially include declarations available in every version of Windows, so you cannot use a function/field/enum value from Windows 8 in a program intended to run in Windows 7, for example.
So just add -D_WIN32_WINNT=0x0600 to your compilation command and leave the header files alone...

about TLS Callback in windows

this is the test code
#include "windows.h"
#include "iostream"
using namespace std;
__declspec(thread) int tls_int = 0;
void NTAPI tls_callback(PVOID, DWORD dwReason, PVOID)
{
tls_int = 1;
}
#pragma data_seg(".CRT$XLB")
PIMAGE_TLS_CALLBACK p_thread_callback = tls_callback;
#pragma data_seg()
int main()
{
cout<<"main thread tls value = "<<tls_int<<endl;
return 0;
}
build with Multi-threaded Debug DLL (/MDd)
run result : main thread tls value = 1
build with Multi-threaded Debug (/MTd)
run result : main thread tls value = 0
Looks like can not capture the main thread created when use the MTd
why ?
While Ofek Shilon is right that the code is missing an ingredient, his answer contains only part of the whole ingredient. Full working solution can be found here which is in turn taken from here.
For explanation on how it works you may refer to this blog (assume we are working with VC++ compiler).
For convenience the code is posted below (note both x86 & x64 platforms are supported):
#include <windows.h>
// Explained in p. 2 below
void NTAPI tls_callback(PVOID DllHandle, DWORD dwReason, PVOID)
{
if (dwReason == DLL_THREAD_ATTACH)
{
MessageBox(0, L"DLL_THREAD_ATTACH", L"DLL_THREAD_ATTACH", 0);
}
if (dwReason == DLL_PROCESS_ATTACH)
{
MessageBox(0, L"DLL_PROCESS_ATTACH", L"DLL_PROCESS_ATTACH", 0);
}
}
#ifdef _WIN64
#pragma comment (linker, "/INCLUDE:_tls_used") // See p. 1 below
#pragma comment (linker, "/INCLUDE:tls_callback_func") // See p. 3 below
#else
#pragma comment (linker, "/INCLUDE:__tls_used") // See p. 1 below
#pragma comment (linker, "/INCLUDE:_tls_callback_func") // See p. 3 below
#endif
// Explained in p. 3 below
#ifdef _WIN64
#pragma const_seg(".CRT$XLF")
EXTERN_C const
#else
#pragma data_seg(".CRT$XLF")
EXTERN_C
#endif
PIMAGE_TLS_CALLBACK tls_callback_func = tls_callback;
#ifdef _WIN64
#pragma const_seg()
#else
#pragma data_seg()
#endif //_WIN64
DWORD WINAPI ThreadProc(CONST LPVOID lpParam)
{
ExitThread(0);
}
int main(void)
{
MessageBox(0, L"hello from main", L"main", 0);
CreateThread(NULL, 0, &ThreadProc, 0, 0, NULL);
return 0;
}
EDIT:
Definitely some explanations are required so let us take a look on what's going on in the code.
If we want to use TLS callbacks then we are to tell the compiler about it explicitly. It is done with the including of the variable _tls_used which has a pointer to the callback array (null-terminated). For the type of this variable you may consult tlssup.c in CRT source code coming along with Visual Studio:
For VS 12.0 by default it lies here: c:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\crt\src\
For VS 14.0 by default it lies here: c:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\crt\src\vcruntime\
It is defined in the following way:
#ifdef _WIN64
_CRTALLOC(".rdata$T") const IMAGE_TLS_DIRECTORY64 _tls_used =
{
(ULONGLONG) &_tls_start, // start of tls data
(ULONGLONG) &_tls_end, // end of tls data
(ULONGLONG) &_tls_index, // address of tls_index
(ULONGLONG) (&__xl_a+1), // pointer to call back array
(ULONG) 0, // size of tls zero fill
(ULONG) 0 // characteristics
};
#else /* _WIN64 */
_CRTALLOC(".rdata$T")
const IMAGE_TLS_DIRECTORY _tls_used =
{
(ULONG)(ULONG_PTR) &_tls_start, // start of tls data
(ULONG)(ULONG_PTR) &_tls_end, // end of tls data
(ULONG)(ULONG_PTR) &_tls_index, // address of tls_index
(ULONG)(ULONG_PTR) (&__xl_a+1), // pointer to call back array
(ULONG) 0, // size of tls zero fill
(ULONG) 0 // characteristics
};
This code initializes values for IMAGE_TLS_DIRECTORY(64) structure which is pointed to by the TLS directory entry. And pointer to call back array is one of its fields. This array is traversed by the OS loader and pointed functions are being called until null pointer is met.
For info about directories in PE file consult this link from MSDN and search for a description of IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES].
x86 note: as you can see, the same name _tls_used is met in tlssup.c for both x86 & x64 platforms, but additional _ is added when including this name for x86 build. It's not a typo but linker feature, so effectively naming __tls_used is taken.
Now we are at the point of creating our callback. Its type can be obtained from the definition of IMAGE_TLS_DIRECTORY(64) which can be found in winnt.h, there is a field
for x64:
ULONGLONG AddressOfCallBacks; // PIMAGE_TLS_CALLBACK *;
and for x86:
DWORD AddressOfCallBacks; // PIMAGE_TLS_CALLBACK *
The type of callbacks is defined as follows (also from winnt.h):
typedef VOID
(NTAPI *PIMAGE_TLS_CALLBACK) (PVOID DllHandle, DWORD Reason, PVOID Reserved);
It is the same as for DllMain and it can handle the same set of events: process\thread attach\detach.
It is time to register callback.
First of all take a look at the code from tlssup.c:
Sections allocated in it:
_CRTALLOC(".CRT$XLA") PIMAGE_TLS_CALLBACK __xl_a = 0;
/* NULL terminator for TLS callback array. This symbol, __xl_z, is never
* actually referenced anywhere, but it must remain. The OS loader code
* walks the TLS callback array until it finds a NULL pointer, so this makes
* sure the array is properly terminated.
*/
_CRTALLOC(".CRT$XLZ") PIMAGE_TLS_CALLBACK __xl_z = 0;
It is very important to know what is special in $ when naming PE section, so the quote from the article named "Compiler and linker support for implicit TLS":
Non-header data in a PE image is placed into one or more sections,
which are regions of memory with a common set of attributes (such as
page protection). The __declspec(allocate(“section-name”)) keyword
(CL-specific) tells the compiler that a particular variable is to be
placed in a specific section in the final executable. The compiler
additionally has support for concatenating similarly-named sections
into one larger section. This support is activated by prefixing a
section name with a $ character followed by any other text. The
compiler concatenates the resulting section with the section of the
same name, truncated at the $ character (inclusive).
The compiler alphabetically orders individual sections when
concatenating them (due to the usage of the $ character in the section
name). This means that in-memory (in the final executable image), a
variable in the “.CRT$XLB” section will be after a variable in the
“.CRT$XLA” section but before a variable in “.CRT$XLZ” section. The C
runtime uses this quirk of the compiler to create an array of null
terminated function pointers to TLS callbacks (with the pointer stored
in the “.CRT$XLZ” section being the null terminator). Thus, in order
to ensure that the declared function pointer resides within the
confines of the TLS callback array being referenced by _tls_used, it
is necessary place in a section of the form “.CRT$XLx“.
There may be actually 2+ callbacks (we will actually use only one) and we may want to call them in order, now we know how. Just place these callbacks in sections named in alphabetical order.
EXTERN_C is added to forbid C++-style name mangling and use a C-style one.
const and const_seg are used for x64 version of the code because otherwise it fails to work, I don't know exact reason for this, the guess may be that CRT sections' access rights are different for x86 & x64 platforms.
And finally we are to include name of the callback function for linker to know it is to be added to the TLS call back array. For note about additional _ for x64 build see the end of p.1 above.
You also must explicitly add the symbol __tls_used. With this your code should work:
#pragma comment(linker,"/include:__tls_used")