Хорошо, как часть моего Lib мне нужно приложение "Worker" для запуска внешней программы. Обычно я бы сделал это с призывом:
system("");
Но на этот раз нужно:
Таким образом, псевдокод будет выглядеть так в идеальной реализации:
CTask::Run()
{
m_iReturnCode = -1;
ExecuteTask(m_strBinaryName);
while(Task_Executing)
{
HeartBeat();
}
return m_iReturnCode;
}
Чтобы уточнить, я запускаю это на платформах Unix.
Каковы мои варианты здесь, popen/fork? Любой, у кого есть хорошее решение, уже работает и может пролить свет на это, пожалуйста?
Спасибо за любой вклад в это.
Я использую систему Linux, повысить для нарезания резьбы и труб, чтобы выполнить команду и получить свой результат (если вы не знаете, повысить вас, конечно, должен смотреть на него).
Я нашел подсказку, чтобы использовать трубу здесь, в stackoverflow, но мне жаль, что я больше не знаю точного вопроса.
Я не добавляю внешний код потока. Просто запустите метод execute
в отдельном потоке.
std::string execute()
{
std::string result;
// DO NOT INTERRUPT THREAD WHILE READING FROM PIPE
boost::this_thread::disable_interruption di;
// add echo of exit code to command to get the exit code
std::string command = mp_command + "; echo $?";
// open pipe, execute command and read input from pipe
FILE* pipe = popen(command.c_str(), "r");
if (pipe)
{
char buffer[128];
while (!feof(pipe))
{
if (fgets(buffer, 128, pipe) != NULL)
{
std::string currBuffer(buffer);
result += currBuffer;
}
}
}
else
{
mp_isValid = false;
}
// sleeping busy wait for the pipe to close
while (pclose(pipe) == -1)
{
boost::this_thread::sleep(boost::posix_time::milliseconds(100));
}
return result;
}
Вы можете создать fork с fork() (или clone(), если хотите потоки), а затем запустить программу с помощью execve() или system() в одном процессе и продолжить запуск исходной программы в другой.
Для кода возврата вы можете получить код возврата даже из вызова system()
как:
ret = system("<your_command>");
printf("%d\n", WEXITSTATUS(ret));
Должно быть какое-то межпроцессное или межпротокольное общение. Если вы не хотите разветвлять его или использовать потоки, вы можете попробовать использовать общий файл. Откройте файл для записи в дочерней задаче (вызывается system()
), и когда вы закончите, напишите некоторое значение (например, "закончено") и закройте файл. В родительской задаче, сердцебиение, пока вы не прочитаете "законченный" из общего файла.
Вы можете это сделать и путем записи глобальной переменной вместо общего файла.
Тем не менее, я бы фортировал или пронизывал его, используя общий файл или глобальную переменную, подвержен ошибкам, и я не совсем уверен, что это сработает.