c# - Detect Boolean value changes inside Thread -
i have c++ dll function want run inside c# thread.
some times need cancel thread, , here issue :
thread.abort() evil multitude of articles i've read on topic
the way use bool , check it's value periodically.
my problem set value true didn't change , still equal false in c++ code. when show messagebox
value changed , works fine. ideas why value changed when messagebox
showed , please tell me how fix issue. c#
public void abortmesh() { if (currmeshstruct.value.meshthread != null && currmeshstruct.value.meshthread.isalive) { //here c++ object , cancel mesh used set bool true; meshcreator.cancelmesh(); } }
c++
stdmethodimp meshcreator::cancelmesh(void) { this->m_stopmesh = true; return s_ok; }
when test boolean value
if (m_stopmesh) return s_false;
the value here false call abortmesh()
if (m_stopmesh) return s_false; messagebox(null,amessage,l"test",null); if (m_stopmesh) // here value changed true return s_false;
the non-deterministic thread abortion (like thread.abort) bad practice. problem is practice allows stop job when job not know stopped.
there no library or framework in .net know of allows write threaded code allow run arbitrary task , abort @ time without dire consequences.
so, write when decided use manual abort using synchronization technique.
solutions:
1) simplest 1 using of volatile boolean variable suggested:
c#
public void abortmesh() { if (currmeshstruct.value.meshthread != null && currmeshstruct.value.meshthread.isalive) { meshcreator.cancelmesh(); } }
c++/cli
public ref class meshcreator { private: volatile system::boolean m_stopmesh; ... } stdmethodimp meshcreator::cancelmesh(void) { this->m_stopmesh = true; return s_ok; } void meshcreator::processmesh(void) { int32 processedparts = 0; while(processedparts != totalpartstoprocess) { continueprocessing(processedparts); processedparts++; if (this->m_stopmesh) { this->makecleanup(); messagebox(null,amessage,l"test",null); } } }
such code should not require synchronization if not make assumptions on completion of thread after cancelmesh
call - not instantaneous , may take variable amount of time happen.
i don't know why use of volatile
didn't you, there few moments check:
- are sure
meshcreator.cancelmesh();
method call happen? - are sure m_stopmesh initialized before actual processing begins?
- are sure check variable inside
processmesh
enough have decent response time worker , not expecting instantaneous?
2)also if use .net 4 or higher try use cancellationtoken-cancellationtokensource model. designed work tasks model works standard threads. won't simplify code taking account async nature of processing code possibly simplify future integration tpl
cancellationtokensource canctokensource = new cancellationtokensource(); cancellationtoken canctoken = canctokensource.token; thread thread = new thread(() => { int32 iteration = 0; while (true) { console.writeline("iteration {0}", iteration); iteration++; thread.sleep(1000); if (canctoken.iscancellationrequested) break; } }); thread.start(); console.writeline("press key cancel..."); console.readkey(); canctokensource.cancel();
3) may want read interlocked class,monitor locks, autoresetevents , other synchronization, not needed in application
edit:
well, don't know how couldn't help(it not best idea, should work such scenario), i'll try later mock app , check issue - possibly has how msvc , csc handle volatile
specifier.
for try use interlocked reads , writes in app:
public ref class meshcreator { private: system::boolean m_stopmesh; ... } stdmethodimp meshcreator::cancelmesh(void) { interlocked::exchange(%(this->m_stopmesh), true); return s_ok; } void meshcreator::processmesh(void) { int32 processedparts = 0; while(processedparts != totalpartstoprocess) { continueprocessing(processedparts); processedparts++; if (interlocked::read(%(this->m_stopmesh)) { this->makecleanup(); messagebox(null,amessage,l"test",null); } } }
p.s.: can post code processes data , checks variable(i don't mean full meshes calculations method, main stages , elements)?
edit: @ least it's clear system about
it possible child processes not exterminated quick enough. read this thread process killing.
p.s.: , edit question more describe system , problem. difficult right answer wrong or incomplete question.
Comments
Post a Comment