3

I have a c++ console application which has an option to be interrupted by pressing any key (implemented by using kbhit()) and in that case it prints what it has done and exits (or can be left to finish the work(some recording) and still prints feedback). I am making a c# gui application for that console application (I'm calling exe file from c# form) and instead of pressing any key on the keyboard, I am using a "stop" button which sends Environment.NewLine (or "\n") to the redirected input and in the c++ application I now have to use something different from kbhit() for it to work. I tried using cin.get(), like:

if (kbhit() || (cin.get() > 0))  
    stop_recording=true;  

but cin.get() is a blocking function, and if I want the console application to run to the end it won't close without pressing the stop button. Is there any function similar to cin.get() that actually isn't blocking, or maybe a different way to send "any key" from c# to my console application process?

Bo Persson
  • 90,663
  • 31
  • 146
  • 203
deckard cain
  • 497
  • 10
  • 24
  • Can you use other Windows synchronization methods like named Mutex or Semaphore? – Alexei Levenkov Apr 23 '12 at 18:07
  • Do you have access to this C++ console application source code? Because if you do, you could implement this through threads: first you would create a thread that will always be listening to the keyboard with cin.get() and then you would run the rest of your application on a separate thread. This way your application will not be blocked. – Felipe Apr 23 '12 at 18:47
  • @AlexeiLevenkov: yes, I have some semaphores in c++ console application, but I don't have the idea how that's going to help. – deckard cain Apr 24 '12 at 08:04
  • @Komyg: I have access to the c++ console application source code, I am supposed to alter it so it can work. Interesting idea about threads, I could try, but the code wasn't written by me and it's a bit complicated, so I'd have to really look into it to make it work. Also, I hope it wouldn't mess up the functionality of the application. – deckard cain Apr 24 '12 at 08:05

3 Answers3

0

use _getch() insted of cin.get(). its a blocking command, but by executing it only if ( _kbhit() ) it will return immediately.

akaltar
  • 1,002
  • 1
  • 19
  • 25
0

You can try to send Ctrl+C to the console process to trigger its break behavior.

You can check named synchronization object if you need to continue - i.e. in your UI process create named Mutex/Semaphore (with random name) and pass this name to the console process. The console process would check once in a while (instead of kbhit) if it still can acquire Mutex/Semaphore and stop when it no longer can.

The other option as suggested by @Komyg is to dedicate a thread for reading console and check if particular input shows up there.

If you expect more communication between the programs search for IPC "inter-process communication" to see more approaches.

Community
  • 1
  • 1
Alexei Levenkov
  • 98,904
  • 14
  • 127
  • 179
0

Found a very simple answer here: Simple example of threading in C++. Credits go to Edward Kmett.
I happened to use boost library in the c++ application so I could use boost threads implementation as well. It was quite simple, this is what my thread function look like:

bool stopped=false;

void inputSent() //
{  
    if (kbhit() || (cin.get() > 0))  
        stopped=true;  

}  

and later in main.cpp:

boost::thread stoppedThread = boost::thread(inputSent);  

After that I just check if stopped==true, and I'm not using stoppedThread.join (I don't know if that's mistake or no, since I don't know when the program ends, if I'm leaving zombie threads behind... maybe someone could enlighten me about that).

Community
  • 1
  • 1
deckard cain
  • 497
  • 10
  • 24