|
@@ -102,10 +102,8 @@ public: |
|
|
|
|
|
|
|
|
if (::pipe(pipe2) != 0) |
|
|
if (::pipe(pipe2) != 0) |
|
|
{ |
|
|
{ |
|
|
try { |
|
|
|
|
|
::close(pipe1[0]); |
|
|
|
|
|
::close(pipe1[1]); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
try { ::close(pipe1[0]); } catch (...) {} |
|
|
|
|
|
try { ::close(pipe1[1]); } catch (...) {} |
|
|
fail("pipe2 creation failed"); |
|
|
fail("pipe2 creation failed"); |
|
|
return false; |
|
|
return false; |
|
|
} |
|
|
} |
|
@@ -134,14 +132,10 @@ public: |
|
|
|
|
|
|
|
|
if ((! fork_exec(argv, &ret)) || ret == -1) |
|
|
if ((! fork_exec(argv, &ret)) || ret == -1) |
|
|
{ |
|
|
{ |
|
|
try { |
|
|
|
|
|
::close(pipe1[0]); |
|
|
|
|
|
::close(pipe1[1]); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
try { |
|
|
|
|
|
::close(pipe2[0]); |
|
|
|
|
|
::close(pipe2[1]); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
try { ::close(pipe1[0]); } catch (...) {} |
|
|
|
|
|
try { ::close(pipe1[1]); } catch (...) {} |
|
|
|
|
|
try { ::close(pipe2[0]); } catch (...) {} |
|
|
|
|
|
try { ::close(pipe2[1]); } catch (...) {} |
|
|
fail("fork_exec() failed"); |
|
|
fail("fork_exec() failed"); |
|
|
return false; |
|
|
return false; |
|
|
} |
|
|
} |
|
@@ -149,12 +143,8 @@ public: |
|
|
fPid = ret; |
|
|
fPid = ret; |
|
|
|
|
|
|
|
|
// fork duplicated the handles, close pipe ends that are used by the child process |
|
|
// fork duplicated the handles, close pipe ends that are used by the child process |
|
|
try { |
|
|
|
|
|
::close(pipe1[0]); |
|
|
|
|
|
} catch(...) {} |
|
|
|
|
|
try { |
|
|
|
|
|
::close(pipe2[1]); |
|
|
|
|
|
} catch(...) {} |
|
|
|
|
|
|
|
|
try { ::close(pipe1[0]); } catch(...) {} |
|
|
|
|
|
try { ::close(pipe2[1]); } catch(...) {} |
|
|
|
|
|
|
|
|
fPipeSend = pipe1[1]; // [1] means writting end |
|
|
fPipeSend = pipe1[1]; // [1] means writting end |
|
|
fPipeRecv = pipe2[0]; // [0] means reading end |
|
|
fPipeRecv = pipe2[0]; // [0] means reading end |
|
@@ -196,10 +186,13 @@ public: |
|
|
++i; |
|
|
++i; |
|
|
continue; |
|
|
continue; |
|
|
} |
|
|
} |
|
|
carla_stderr("we have waited for child with pid %d to appear for %.1f seconds and we are giving up", (int)fPid, (float)WAIT_START_TIMEOUT / 1000.0f); |
|
|
|
|
|
|
|
|
carla_stderr("we have waited for child with pid %d to appear for %.1f seconds and we are giving up", int(fPid), float(WAIT_START_TIMEOUT)/1000.0f); |
|
|
} |
|
|
} |
|
|
else |
|
|
else |
|
|
carla_stderr("read() failed: %s", std::strerror(errno)); |
|
|
|
|
|
|
|
|
{ |
|
|
|
|
|
CarlaString error(std::strerror(errno)); |
|
|
|
|
|
carla_stderr("read() failed: %s", error.buffer()); |
|
|
|
|
|
} |
|
|
break; |
|
|
break; |
|
|
|
|
|
|
|
|
case 1: |
|
|
case 1: |
|
@@ -223,20 +216,16 @@ public: |
|
|
|
|
|
|
|
|
if (kill(fPid, SIGKILL) == -1) |
|
|
if (kill(fPid, SIGKILL) == -1) |
|
|
{ |
|
|
{ |
|
|
carla_stderr("kill() failed: %s (start)\n", std::strerror(errno)); |
|
|
|
|
|
|
|
|
CarlaString error(std::strerror(errno)); |
|
|
|
|
|
carla_stderr("kill() failed: %s (start)\n", error.buffer()); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
// wait a while child to exit, we dont like zombie processes |
|
|
// wait a while child to exit, we dont like zombie processes |
|
|
wait_child(fPid); |
|
|
wait_child(fPid); |
|
|
|
|
|
|
|
|
// close pipes |
|
|
// close pipes |
|
|
try { |
|
|
|
|
|
::close(fPipeRecv); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
|
|
|
try { |
|
|
|
|
|
::close(fPipeSend); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
try { ::close(fPipeRecv); } catch (...) {} |
|
|
|
|
|
try { ::close(fPipeSend); } catch (...) {} |
|
|
|
|
|
|
|
|
fPipeRecv = -1; |
|
|
fPipeRecv = -1; |
|
|
fPipeSend = -1; |
|
|
fPipeSend = -1; |
|
@@ -261,13 +250,8 @@ public: |
|
|
|
|
|
|
|
|
waitChildClose(); |
|
|
waitChildClose(); |
|
|
|
|
|
|
|
|
try { |
|
|
|
|
|
::close(fPipeRecv); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
|
|
|
try { |
|
|
|
|
|
::close(fPipeSend); |
|
|
|
|
|
} catch (...) {} |
|
|
|
|
|
|
|
|
try { ::close(fPipeRecv); } catch (...) {} |
|
|
|
|
|
try { ::close(fPipeSend); } catch (...) {} |
|
|
|
|
|
|
|
|
fPipeRecv = -1; |
|
|
fPipeRecv = -1; |
|
|
fPipeSend = -1; |
|
|
fPipeSend = -1; |
|
@@ -288,7 +272,7 @@ public: |
|
|
if (locale == nullptr) |
|
|
if (locale == nullptr) |
|
|
{ |
|
|
{ |
|
|
locale = carla_strdup(setlocale(LC_NUMERIC, nullptr)); |
|
|
locale = carla_strdup(setlocale(LC_NUMERIC, nullptr)); |
|
|
setlocale(LC_NUMERIC, "POSIX"); |
|
|
|
|
|
|
|
|
::setlocale(LC_NUMERIC, "POSIX"); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
fIsReading = true; |
|
|
fIsReading = true; |
|
@@ -300,7 +284,7 @@ public: |
|
|
|
|
|
|
|
|
if (locale != nullptr) |
|
|
if (locale != nullptr) |
|
|
{ |
|
|
{ |
|
|
setlocale(LC_NUMERIC, locale); |
|
|
|
|
|
|
|
|
::setlocale(LC_NUMERIC, locale); |
|
|
delete[] locale; |
|
|
delete[] locale; |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
@@ -610,9 +594,9 @@ private: |
|
|
|
|
|
|
|
|
static bool wait_child(const pid_t pid) noexcept |
|
|
static bool wait_child(const pid_t pid) noexcept |
|
|
{ |
|
|
{ |
|
|
if (pid == -1) |
|
|
|
|
|
|
|
|
if (pid <= 0) |
|
|
{ |
|
|
{ |
|
|
carla_stderr2("Can't wait for pid -1"); |
|
|
|
|
|
|
|
|
carla_stderr2("Can't wait for pid %i", int(pid)); |
|
|
return false; |
|
|
return false; |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
@@ -622,10 +606,7 @@ private: |
|
|
{ |
|
|
{ |
|
|
try { |
|
|
try { |
|
|
ret = ::waitpid(pid, nullptr, WNOHANG); |
|
|
ret = ::waitpid(pid, nullptr, WNOHANG); |
|
|
} |
|
|
|
|
|
catch(...) { |
|
|
|
|
|
break; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
} CARLA_SAFE_EXCEPTION_BREAK("wait_child"); |
|
|
|
|
|
|
|
|
if (ret != 0) |
|
|
if (ret != 0) |
|
|
{ |
|
|
{ |
|
@@ -637,7 +618,8 @@ private: |
|
|
if (errno == ECHILD) |
|
|
if (errno == ECHILD) |
|
|
return true; |
|
|
return true; |
|
|
|
|
|
|
|
|
carla_stderr2("waitpid(%i) failed: %s", int(pid), std::strerror(errno)); |
|
|
|
|
|
|
|
|
CarlaString error(std::strerror(errno)); |
|
|
|
|
|
carla_stderr2("waitpid(%i) failed: %s", int(pid), error.buffer()); |
|
|
return false; |
|
|
return false; |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|