@@ -121,30 +121,24 @@ void CRenderDevice::End(void)
121121#endif
122122#endif // !DEDICATED_SERVER
123123}
124- static volatile u32 mt_Thread_marker = 0x12345678 ;
125- void mt_Thread (void * ptr )
124+
125+ void CRenderDevice::SecondaryThreadProc (void *context )
126126{
127+ auto &device = *static_cast <CRenderDevice*>(context);
127128 while (true )
128129 {
129- // waiting for Device permission to execute
130- Device.mt_csEnter .Enter ();
131- if (Device.mt_bMustExit )
130+ device.syncProcessFrame .Wait ();
131+ if (device.mt_bMustExit )
132132 {
133- Device .mt_bMustExit = FALSE ; // Important!!!
134- Device. mt_csEnter . Leave (); // Important!!!
133+ device .mt_bMustExit = FALSE ;
134+ device. syncThreadExit . Set ();
135135 return ;
136136 }
137- mt_Thread_marker = Device.dwFrame ;
138- for (u32 pit = 0 ; pit < Device.seqParallel .size (); pit++)
139- Device.seqParallel [pit]();
140- Device.seqParallel .clear_not_free ();
141- Device.seqFrameMT .Process (rp_Frame);
142- // now we give control to device - signals that we are ended our work
143- Device.mt_csEnter .Leave ();
144- // waits for device signal to continue - to start again
145- Device.mt_csLeave .Enter ();
146- // returns sync signal to device
147- Device.mt_csLeave .Leave ();
137+ for (u32 pit = 0 ; pit < device.seqParallel .size (); pit++)
138+ device.seqParallel [pit]();
139+ device.seqParallel .clear_not_free ();
140+ device.seqFrameMT .Process (rp_Frame);
141+ device.syncFrameDone .Set ();
148142 }
149143}
150144
@@ -242,11 +236,7 @@ void CRenderDevice::on_idle()
242236 mFullTransform_saved = mFullTransform ;
243237 mView_saved = mView ;
244238 mProject_saved = mProject ;
245- // *** Resume threads
246- // Capture end point - thread must run only ONE cycle
247- // Release start point - allow thread to run
248- mt_csLeave.Enter (); // prevent secondary thread to proceed with the next frame
249- mt_csEnter.Leave (); // allow secondary thread to do its work
239+ syncProcessFrame.Set (); // allow secondary thread to do its job
250240 Sleep (0 );
251241
252242#ifndef DEDICATED_SERVER
@@ -266,19 +256,7 @@ void CRenderDevice::on_idle()
266256 renderTotalReal.FrameEnd ();
267257 stats.RenderTotal .accum = renderTotalReal.accum ;
268258#endif // #ifndef DEDICATED_SERVER
269- // *** Suspend threads
270- // Capture startup point
271- // Release end point - allow thread to wait for startup point
272- mt_csEnter.Enter (); // wait for secondary thread to finish its work
273- mt_csLeave.Leave (); // allow secondary thread to wait for its work in the next frame
274- // Ensure, that second thread gets chance to execute anyway
275- if (dwFrame!=mt_Thread_marker)
276- {
277- for (u32 pit = 0 ; pit < Device.seqParallel .size (); pit++)
278- Device.seqParallel [pit]();
279- Device.seqParallel .clear_not_free ();
280- seqFrameMT.Process (rp_Frame);
281- }
259+ syncFrameDone.Wait (); // wait until secondary thread finish its job
282260#ifdef DEDICATED_SERVER
283261 u32 FrameEndTime = TimerGlobal.GetElapsed_ms ();
284262 u32 FrameTime = (FrameEndTime - FrameStartTime);
@@ -338,17 +316,17 @@ void CRenderDevice::Run()
338316 Timer_MM_Delta = time_system - time_local;
339317 }
340318 // Start all threads
341- mt_csEnter.Enter ();
342319 mt_bMustExit = FALSE ;
343- thread_spawn (mt_Thread , " X-RAY Secondary thread" , 0 , 0 );
320+ thread_spawn (SecondaryThreadProc , " X-RAY Secondary thread" , 0 , this );
344321 // Message cycle
345322 seqAppStart.Process (rp_AppStart);
346323 Render->ClearTarget ();
347324 message_loop ();
348325 seqAppEnd.Process (rp_AppEnd);
349326 // Stop Balance-Thread
350327 mt_bMustExit = TRUE ;
351- mt_csEnter.Leave ();
328+ syncProcessFrame.Set ();
329+ syncThreadExit.Wait ();
352330 while (mt_bMustExit)
353331 Sleep (0 );
354332}
0 commit comments