?
Solved

C++ CreateThread doesn't call function

Posted on 2006-07-16
9
Medium Priority
?
901 Views
Last Modified: 2012-06-21
Hello,

i got a multithreaded dll compiled with Microsoft Visual C++ 6.
The code looks similar to this:

DWORD WINAPI oncommand(PVOID params)
{
      MessageBox(0, "test01", "test", 0);
}
BOOL APIENTRY DllMain(HANDLE hModule, DWORD reason, LPVOID lpReserved)
{
      unsigned long cthreadid;
      CreateThread(NULL, 0, &oncommand, 0, 0, &cthreadid);
      Sleep(10000);
}

When i compile this dll with the /MT parameter turned on, the desired messagebox doesn't pop up.
It seems, that the CreateThread function does for some odd reason not work.
Any suggestions on how to solve that?
0
Comment
Question by:MLeandroK
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
9 Comments
 
LVL 86

Expert Comment

by:jkr
ID: 17119225
You are passing teh thread proc incorrectly, that should be

BOOL APIENTRY DllMain(HANDLE hModule, DWORD reason, LPVOID lpReserved)
{
     unsigned long cthreadid;
     CreateThread(NULL, 0, oncommand, 0, 0, &cthreadid); // *no* '&' with the thread proc
     Sleep(10000);
}

If you use the ampersand, you pass the address of the address of the function, that's why it does not work.
0
 
LVL 86

Expert Comment

by:jkr
ID: 17119239
As a side note, it's always good to check for errors when calling a Win32 API function, e.g. like

BOOL APIENTRY DllMain(HANDLE hModule, DWORD reason, LPVOID lpReserved)
{
     unsigned long cthreadid;
     HANDLE hThread = CreateThread(NULL, 0, oncommand, 0, 0, &cthreadid);
    if (!hThread) {

        char buf[256];

        wsprintf(buf,"Error creating thread, reason %d", GetLastError());
        MessageBox(0, buf, "test error", MB_OK);
    }
     Sleep(10000);
}

0
 
LVL 86

Expert Comment

by:jkr
ID: 17119287
>>If you use the ampersand, you pass the address of the address of the function, that's why it does not
>> work.

Just to be clear on that - in C/C++, the name of a function is equal to it's address, that's why that single ampersand before the name has caused things to go down the drain for the reason above.
0
VIDEO: THE CONCERTO CLOUD FOR HEALTHCARE

Modern healthcare requires a modern cloud. View this brief video to understand how the Concerto Cloud for Healthcare can help your organization.

 
LVL 12

Expert Comment

by:rajeev_devin
ID: 17119538
The problem is not with the &. You can use both.
As jkr suggested the name of the function is sufficient as the function address.
But you can also append & before it.
The both values will be same.

Make sure that your DLL is not loaded before.
0
 
LVL 48

Expert Comment

by:AlexFM
ID: 17119677
Remove Steep, replace MessageBox with TRACE or OutputDebugString and test this again. What result do you have?
BTW, thread should not be created in DllMain, you need to add exported function for this.
0
 

Author Comment

by:MLeandroK
ID: 17120808
I now tried both parameters &oncommand and oncommand without the & symbol, neither of them works.
I also appended the code
if (!hThread)
{
        char buf[256];
        wsprintf(buf,"Error creating thread, reason %d", GetLastError());
        MessageBox(0, buf, "test error", MB_OK);
}
as written by jkr, but hThread seems to have a value, consequently it doesn't enter the if-loop.
When i forced the content of the if-loop to be executed, the return of GetLastError() was equal to 0.

I should probably also add that the exact same code has worked (at least i'm pretty sure it was the same, unless code rewrites itself) and now suddenly doesn't.
So i personally think it's rather a compiler issue.
0
 

Author Comment

by:MLeandroK
ID: 17120818
And i almost forgot thanks for the answers.
Any futher suggestions on how to solve this?
0
 
LVL 14

Accepted Solution

by:
wayside earned 2000 total points
ID: 17122072
How does your dll get loaded?

You should set a break-point in your thread function and see if it ever gets called.

If it does, check the return value from the MessageBox() call, if 0 use GetLastError() to see what the error is.

In general it is a Bad Idea to do anything substantive in DllMain(), especially if your dll is implicitly loaded.

Also, the MSDN page for CreateThread() says the following:

"During process startup and DLL initialization routines, new threads can be created, but they do not begin execution until DLL initialization is done for the process."

This clearly states that your thread won't run until DllMain() returns, which won't be until after your Sleep(10000) finishes. Are you waiting 10 seconds or are you killing your program right away when the message box doesn't appear?
0
 

Author Comment

by:MLeandroK
ID: 17122901
"This clearly states that your thread won't run until DllMain() returns"
this is the golden line i've been waiting for
thanks wayside, it works now.
0

Featured Post

On Demand Webinar: Networking for the Cloud Era

Did you know SD-WANs can improve network connectivity? Check out this webinar to learn how an SD-WAN simplified, one-click tool can help you migrate and manage data in the cloud.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction This article is the first in a series of articles about the C/C++ Visual Studio Express debugger.  It provides a quick start guide in using the debugger. Part 2 focuses on additional topics in breakpoints.  Lastly, Part 3 focuses on th…
This article shows you how to optimize memory allocations in C++ using placement new. Applicable especially to usecases dealing with creation of large number of objects. A brief on problem: Lets take example problem for simplicity: - I have a G…
The goal of the video will be to teach the user the concept of local variables and scope. An example of a locally defined variable will be given as well as an explanation of what scope is in C++. The local variable and concept of scope will be relat…
The viewer will learn how to user default arguments when defining functions. This method of defining functions will be contrasted with the non-default-argument of defining functions.
Suggested Courses

770 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question