Click to See Complete Forum and Search --> : threds in a loop, how to close the HANDLEs


armada
July 15th, 2009, 12:09 PM
Hello folks,

I'm new to C++, hence I hit the brick by playing with threads!
See the following code



#include "MyApp.h"


void MyApp::print()
{
for (int i = loopStart; i <= loopEnd; ++i)
{
if (i % dispFrequency == 0)
{
printf( "%d: i = %d\n", threadName, i );
}
}
printf( "%d thread terminating\n", threadName );
}


void MyApp::setName(int &t)
{
#ifdef WITH_SYNCHRONIZATION
EnterCriticalSection( &m_CriticalSection );
#endif
threadName = t;
#ifdef WITH_SYNCHRONIZATION
LeaveCriticalSection( &m_CriticalSection );
#endif
}

int main()
{


HANDLE threads[CPU];
unsigned uiThread1ID[CPU];


for(int i = 0; i < CPU; i++)
{
MyApp *o1 = new MyApp(0, 1000000, 20000);
o1->setName(i); //critical section

threads[i] = (HANDLE)_beginthreadex( NULL, // security
0, // stack size
MyApp::ThreadStaticEntryPoint,
o1, // arg list
0,
&uiThread1ID[i] );
if ( threads[i] == 0 )
printf("Failed to create thread 1\n");

//DWORD dwExitCode;
//GetExitCodeThread( threads[i], &dwExitCode ); // should be STILL_ACTIVE = 0x00000103 = 259
//printf( "initial thread %d exit code = %u\n", i, dwExitCode );

}

WaitForMultipleObjects(CPU, threads, true, INFINITE);

printf("This pain has ended!\n");
}


2 issues:

1.
now when I move o1 pointer declaration outside the for loop, exmp in line 37, then there is no interleaving at all, it is executing only the last loop, cor CPU = 5, I get only the last loop i = 4.
But, with the pointer as it is, it works fine, however, creating so many pointers in the loop, I find it inefficient isn't it ?
Furthermore, with the code as it is, when I add the following lines (in the for loop):
delete o1;
o1 = NULL;

My application is behaving strange, and in Win 7 is reporting an error. Why is that? really strange.

2.*
how does one close HANDLEs in this fashion? In one by one, manual thread creation I used to simply call this
CloseHandle( hth1 );

Or should I still call this in a seperate loop or there is a better way todo so?


thank you in advance!

Arjay
July 15th, 2009, 12:52 PM
Please post the thread proc code and the complete MyApp class code.

I don't see where you initialize the critical section to protect the threadName variable.

You are only half way synchronizing the threadName variable. You do it for the write operation (in setName()), but you don't do it when you read from the variable (e.g. print() method). You need to do it all places that access a shared variable.

With regard to synchronizing an int variable. On Windows, consider using the InterlockedExchangeXXX family of functions.

Consider using a RAII approach to synchronization rather than the explicit critical section Enter/Leave calls. See my subject line for articles.

You are leaking memory on each 'new MyApp(...)' allocation.

Windows 7 may not like your app because it's leaking memory and thread handles.

To clean up handles, consider wrapping the threading functionality into a class with an overridden method that performs the work. The class is responsible for closing its own thread handle. Each time through the loop, you create a class instance and push it onto a std::vector of class pointers. For cleanup, you cycle through the vector and delete each class object (which in turn, closes any thread handles).

armada
July 15th, 2009, 01:43 PM
Consider using a RAII approach to synchronization rather than the explicit critical section Enter/Leave calls. See my subject line for articles.

You are leaking memory on each 'new MyApp(...)' allocation.

Windows 7 may not like your app because it's leaking memory and thread handles.

To clean up handles, consider wrapping the threading functionality into a class with an overridden method that performs the work. The class is responsible for closing its own thread handle. Each time through the loop, you create a class instance and push it onto a std::vector of class pointers. For cleanup, you cycle through the vector and delete each class object (which in turn, closes any thread handles).

Arjay, thanx for your reply.
However, I don't really understand your reply, as said I'm beginner in C++, therefore more explicit answer would have been more understandable indeed.
The thing with synchronization is not important for now, I was just following a tutorial.
Can you tell me more about cleaning the handles, that thread class??

"You are leaking memory on each 'new MyApp(...)' allocation." Can you explain why am I doing so?

How about that RAII, I didnt get it, where can I learn about that ?


thank you!

Arjay
July 15th, 2009, 01:55 PM
"You are leaking memory on each 'new MyApp(...)' allocation." Can you explain why am I doing so?

How about that RAII, I didnt get it, where can I learn about that ?


thank you!

A basic concept of C++ is that for each time you allocate memory with 'new', you need to free it with a corresponding call to 'delete'.

I have thread synchronization articles listed in my signature line. If you can't see them, you need to enable this in your control panel.

To do this:
1) Click on UserCP on the left about 3" down the page.
2) In Settings & Options, click 'Edit Options'
3) Under 'Thread Display Options', check 'Show Signatures'

armada
July 16th, 2009, 03:58 PM
To clean up handles, consider wrapping the threading functionality into a class with an overridden method that performs the work. The class is responsible for closing its own thread handle. Each time through the loop, you create a class instance and push it onto a std::vector of class pointers. For cleanup, you cycle through the vector and delete each class object (which in turn, closes any thread handles).


I tried to read your tutorials, but I didnt understand a lot, too compliacted!
Can you give an example for the above? A concrete example would be very much of use.

thanx

Arjay
July 16th, 2009, 04:31 PM
I tried to read your tutorials, but I didnt understand a lot, too compliacted!
Can you give an example for the above? A concrete example would be very much of use.

thanxThe articles are basic multi-threading articles. Hopefully, you've downloaded the source code, compiled the sample programs, and stepped through the programs in a debugger. If you've already done this and still find them too difficult, you might need to start with a basic C++ tutorial.

armada
July 17th, 2009, 07:26 AM
Hi,

Can you tell me how to add object into array and how to delete afterwards, so that they call their corresponding close handle ()?

thanx