5
votes

In main, I give the user the ability to enter a command to stop the application:

while( run_processes && cin >> command_line_input ){

I'd also like to stop the application elsewhere by setting run_processes = false;.

However, when I set run_processes to false, the above loop doesn't stop without the user entering input.

How can I properly interrupt the loop without the user entering input?

3
show more code : where and how exactly do you set it to false ?quantdev
@quantdev In another boost thread. I apologize for leaving out a key detail, that I'd like the loop to stop without user input. I've confirmed that run_processes is properly being set. Does cin not necessarily depend upon user input for the while to proceed? Thank you so much in advance!user1382306
If you create another thread which calls cin >> command_line_input (and then send the string to the main thread), then you can decide in the main thread not to wait for thread reading from cin. I don't think it's possible to abort the cin >> command_line_input call itself in a portable way.pts

3 Answers

7
votes

It is not possible to interrupt std::cin in a portable way.

You could however resolve to non-portable solution, e.g. manually poll() the standard input on a UNIX system and check run_processes while polling.

0
votes

Does cin not necessarily depend upon user input for the while to proceed?

Yes, the user would have to enter input each loop.

bool stop = false;
std::string command;
int count = 0;
while(stop==false && std::cin>>command)
{
    ++count;
    std::cout<<count<<std::endl;
}

The code above only counts +1 after I enter something. Unless you are changing the value of run_process based on the user input I don't see why it shouldn't work...?

0
votes

I don't know if the following solution is standard enough, but it works on both my Fedora Linux (GCC 10.3) & Windows 10 (MSVC 16.11)

#include <iostream>
#include <csignal>

int main()
{
    std::signal(SIGINT, [] (int s)
    {
        std::signal(s, SIG_DFL);
        std::fclose(stdin);
        std::cin.setstate(std::ios::badbit); // To differenciate from EOF input
    });

    std::string input;
    while (std::getline(std::cin, input));

    std::cout << (std::cin.bad() ? "interrupted" : "eof") << std::endl;
}

Don't ask me how to reuse cin from that state now.