///////////////////////////////////////////////////////////////////// // starve.cpp - demonstrate starvation condition // // // // Two threads attempt to run to completion, but second one // // has lower priority, so only first finishes. // // // // Jim Fawcett, CSE691 - Software Modeling & Analysis, Fall 2000 // ///////////////////////////////////////////////////////////////////// #include #include #include using namespace std; int count1 = 0; int count2 = 0; //----< thread processing function >--------------------------- unsigned int __stdcall threadProc1(void *pEventHandle) { HANDLE event = *((HANDLE*)pEventHandle); WaitForSingleObject(event,INFINITE); int i, j, x=1; for(i=0; i<100; i++) { for(j=0; j<100; j++) ++count1; Sleep(0); } return 0; } //----< thread processing function >--------------------------- unsigned int __stdcall threadProc2(void *pEventHandle) { HANDLE event = *((HANDLE*)pEventHandle); WaitForSingleObject(event,INFINITE); int i, j, x=1; for(i=0; i<100; i++) { for(j=0; j<100; j++) ++count2; Sleep(0); } return 0; } // //----< entry point for process >------------------------------ void main() { cout << "\n Demonstrate the Operation of Mult-threaded Code " << "\n With Starvation Condition" << "\n=======================================================\n\n"; // define an array of handles to threads, needed to wait // for their completion const int NumHandles = 2; HANDLE thHand[NumHandles]; // This event forces both threads to wait until main invokes // SetEvent(event). That makes sure that the two threads // start at the same time. HANDLE event = CreateEvent( NULL, // default security attributes TRUE, // require manual reset FALSE, // initial state is unsignaled NULL // event name ); // define argument values for thread #1 _beginthreadex string shared; void* Security = NULL; // no security attributes unsigned int StackSize = 0; // stack size picked by OS unsigned int(__stdcall threadProc1)(void*); // name of thread function unsigned int InitFlag = 0; // start running unsigned int ThreadID[2]; // receives thread id void *Arg1 = &event; // pointer to event handle // start first thread thHand[0] = (HANDLE)_beginthreadex( Security, StackSize, threadProc1, Arg1, InitFlag, &ThreadID[0] ); SetThreadPriority(thHand[0],THREAD_PRIORITY_NORMAL); // // define argument values for thread #2 _beginthreadex void *Arg2 = &event; // start second thread thHand[1] = (HANDLE)_beginthreadex( Security, StackSize, threadProc2, Arg2, InitFlag, &ThreadID[1] ); SetThreadPriority(thHand[1],THREAD_PRIORITY_HIGHEST); Sleep(100); // make sure both threads are initialized SetEvent(event); // start both threads - they both wait for this event // tell process to wait for both threads to complete // before terminating BOOL fwait = FALSE; // wait for first unsignaled handle DWORD timeOut = INFINITE; // time out in milliseconds WaitForMultipleObjects(NumHandles, thHand, fwait, timeOut); CloseHandle(thHand[0]); // return resources CloseHandle(thHand[1]); // return resources cout << "\n count1 = " << count1 << "\n count2 = " << count2 << "\n\n"; }