LabWindows/CVI

cancel
Showing results for 
Search instead for 
Did you mean: 

How can I exit completely from a thread in LabWindows/CVI?

       

        Hello,

        I want to exit completely from a thread, that I composed in my code, when I click the 'Kapat' button that I composed in my user interface. I used 'CmtExitThreadPoolThread (0)' function and

 'CmtReleaseThreadPoolFunctionID (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId)'  function; but the compiler gave an error in CmtExitThreadPoolThread (0).

 

       What is the reason of this error?

 

      

        The following is a part of the my code:

 

 

int CVICALLBACK CBTestleriKapat (int panel, int control, int event,
         void *callbackData, int eventData1, int eventData2)
{
 switch (event)
 {
  case EVENT_COMMIT:
   //CmtWaitForThreadPoolFunctionCompletion (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId, OPT_TP_PROCESS_EVENTS_WHILE_WAITING);
   CmtExitThreadPoolThread (0);  
   CmtReleaseThreadPoolFunctionID (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId);
   //CmtExitThreadPoolThread (0);
   
   DiscardPanel(testler);
   break;
  case EVENT_RIGHT_CLICK:

   break;
 }
 return 0;
}

 


double sonuc;
int plot_handle;
static int CVICALLBACK GraphLoop (void *functionData)                 // 'GraphLoop' function is my thread function. 
{
 FILE *fp;
 int i;
 fp=fopen(fileName,"a");
 fprintf(fp,"\n\n Input Number     Amplitude      Upper Level     Lower Level   Status\n\n");
 for(i=0;i<1024;i++)
 {
  hpe363xa_queryOutputVolt3631 (vi, 1, &sonuc);
  lowerlevel[i]=-3;
  upperlevel[i]=3;
    
  amplitude[i] = sonuc;
  if (amplitude[i] > upperlevel[i] || amplitude[i] < lowerlevel[i])
  {
   status[i]='F';
  }
  else
  {
      status[i]='P';
  }
  
  fprintf(fp,"   %d        %9.5f       %9.5f       %9.5f        %c\n",inputNumber[i], amplitude[i], upperlevel[i], lowerlevel[i], status[i]);
  
  inputNumber[i]=i+1;
  
  plot_handle = PlotXY (testler, TESTLER_GRAPH, inputNumber, amplitude, i+1, VAL_INTEGER, VAL_DOUBLE, VAL_THIN_LINE, VAL_EMPTY_SQUARE, VAL_DOT, 1, VAL_RED);
  
        //PlotXY (testler, TESTLER_GRAPH, inputNumber, lowerlevel, 1024, VAL_INTEGER, VAL_DOUBLE, VAL_THIN_LINE, VAL_EMPTY_SQUARE, VAL_SOLID, 1, VAL_RED);
   
  //PlotXY (testler, TESTLER_GRAPH, inputNumber, upperlevel, 1024, VAL_INTEGER, VAL_DOUBLE, VAL_THIN_LINE, VAL_EMPTY_SQUARE, VAL_SOLID, 1, VAL_RED);
 }
 fclose(fp);
 return 0;

 

 

int CVICALLBACK CBBasla (int panel, int control, int event,
       void *callbackData, int eventData1, int eventData2)                                        // The program will enter to the thread when the user clicks the 'Basla' button.
{
 switch (event)
 {
  case EVENT_COMMIT:
   
   CmtScheduleThreadPoolFunction (DEFAULT_THREAD_POOL_HANDLE, GraphLoop, NULL, &GraphLoopId);
   CmtWaitForThreadPoolFunctionCompletion (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId, OPT_TP_PROCESS_EVENTS_WHILE_WAITING); 
   CmtReleaseThreadPoolFunctionID (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId);  
   
   break;
  case EVENT_RIGHT_CLICK:

   break;
 }
 return 0;
}

  

0 Kudos
Message 1 of 4
(4,800 Views)

What error is the compiler giving?

 

Here are some resources regarding this topic that may shed more light:

 

CmtExitThreadPoolThread

http://zone.ni.com/reference/en-XX/help/370051Y-01/cvi/libref/cvicmtexitthreadpoolthread/

 

CmtReleaseThreadPoolFunctionID

http://zone.ni.com/reference/en-XX/help/370051V-01/cvi/libref/cvicmtreleasethreadpoolfunctionid/

 

http://forums.ni.com/t5/LabWindows-CVI/Must-CmtReleaseThreadPoolFunctionID-be-called-from-the-thread...

 

^ this forum contains some links to other useful articles too

Michael Keane
National Instruments
0 Kudos
Message 2 of 4
(4,767 Views)

             

           Hello,

           I think that I could not explain completely my problem. I will explain better my problem:

         


#include <utility.h>
#include <ansi_c.h>
#include <cvirte.h>
#include <userint.h>
#include "Ornek.h"
CmtThreadPoolHandle *poolHandle;

static int PANEL, testler, panelHandle;
char fileName[300]="result.txt";
int GraphLoopId=0;

int main (int argc, char *argv[])
{
if (InitCVIRTE (0, argv, 0) == 0)
return -1; /* out of memory */
if ((testler = LoadPanel (0, "Example.uir", TESTLER)) < 0)
return -1;
DisplayPanel (testler);
RunUserInterface ();
DiscardPanel (testler);
return 0;
}

//The Callback function that is expected to stop the thread
int CVICALLBACK CBStop (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
CmtExitThreadPoolThread (0);
CmtReleaseThreadPoolFunctionID (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId);
DiscardPanel(testler);

break;
case EVENT_RIGHT_CLICK:

break;
}
return 0;
}


// 'GraphLoop' function is my thread function.
static int CVICALLBACK GraphLoop (void *functionData)
{
FILE *fp;
int i;
fp=fopen(fileName,"a");

for(i=0;i<100000000;i++)
{
fprintf(fp," %d ",i)
}
return 0;
}

// The program will enter to the thread when the user clicks the 'Start' button.
int CVICALLBACK CBStart (int panel, int control, int event, void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:

CmtScheduleThreadPoolFunction (DEFAULT_THREAD_POOL_HANDLE, GraphLoop, NULL, &GraphLoopId);
CmtWaitForThreadPoolFunctionCompletion (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId, OPT_TP_PROCESS_EVENTS_WHILE_WAITING);
CmtReleaseThreadPoolFunctionID (DEFAULT_THREAD_POOL_HANDLE, GraphLoopId);

break;
case EVENT_RIGHT_CLICK:
break;
}
return 0;
}

int CVICALLBACK CBTestler (int panel, int event, void *callbackData,
int eventData1, int eventData2)
{
switch (event)
{
case EVENT_GOT_FOCUS:

break;
case EVENT_LOST_FOCUS:

break;
case EVENT_CLOSE:
DiscardPanel (testler);

break;
}
return 0;
}


          There are 3 fuctions;
1.Thread fuction, writing numbers into a file
2.Start button callback, starting the thread.
3.Stop button callback, stopping the thread safely

 

         There are example codes about theading and how to use threads, but all of them uses "While" loop. In c#, we successfully start and stop(by using Thread.Abort) the executing thread safely. When we back to the LabWindows/CVI, we could not find any structure to stop the thread, like in the example above, safely.

 

          When I press the stop button, I get the following error;

NON-FATAL RUN-TIME ERROR: "Example.c", line 47, col 13, thread id 0x0000094C: Library function error (return value == -14926 [0xffffc5b2]). You can only perform this operation on a thread pool thread.

 

          The compiler gives this error for that line:

          CmtExitThreadPoolThread (0);

 

          How can I correct this error?

          

0 Kudos
Message 3 of 4
(4,747 Views)

eren,

you have opened two discussions on very similar topics: the present one and this other one. Are they related? If so, you should avoid to do the same in the future as it becomes very difficult to properly handle the situation.

 

Regarding the error you are receiving, it's very clear: you haven't started a thread pool (using CmtNewThreadPool) so calling ExitThreadPoolThread cannot be issued. Additionally, that function is intended to be called from within the thread itself, not from an external function.

 

What do you mean by "exit completely from a thread"? When the function started with CmtScheduleThreadPoolFunction terminates the thread ends and can be released, so after CmtWaitForThreadPoolFunctionCompletion succesfully returns the tread is ended. Can the second option given in my anser in the other thread be a solution to your needs?



Proud to use LW/CVI from 3.1 on.

My contributions to the Developer Community
________________________________________
If I have helped you, why not giving me a kudos?
0 Kudos
Message 4 of 4
(4,739 Views)