26 enum { magicMastSlaveConnectionHeader = 0x712baf04 };
28 static const char* startMessage =
"__ipc_st";
29 static const char* killMessage =
"__ipc_k_";
30 static const char* pingMessage =
"__ipc_p_";
31 enum { specialMessageSize = 8, defaultTimeoutMs = 8000 };
33 static inline bool isMessageType (
const MemoryBlock& mb,
const char* messageType) noexcept
35 return mb.matches (messageType, (
size_t) specialMessageSize);
38 static String getCommandLinePrefix (
const String& commandLineUniqueID)
40 return "--" + commandLineUniqueID +
":";
54 void pingReceived() noexcept { countdown = timeoutMs / 1000 + 1; }
57 virtual bool sendPingMessage (
const MemoryBlock&) = 0;
58 virtual void pingFailed() = 0;
65 void handleAsyncUpdate()
override { pingFailed(); }
71 if (--countdown <= 0 || ! sendPingMessage ({ pingMessage, specialMessageSize }))
73 triggerConnectionLostMessage();
93 if (createPipe (pipeName, timeoutMs))
103 void connectionMade()
override {}
104 void connectionLost()
override { owner.handleConnectionLost(); }
106 bool sendPingMessage (
const MemoryBlock& m)
override {
return owner.sendMessageToSlave (m); }
107 void pingFailed()
override { connectionLost(); }
109 void messageReceived (
const MemoryBlock& m)
override 113 if (m.
getSize() != specialMessageSize || ! isMessageType (m, pingMessage))
114 owner.handleMessageFromSlave (m);
119 JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (
Connection)
134 if (connection !=
nullptr)
135 return connection->sendMessage (mb);
142 int timeoutMs,
int streamFlags)
150 args.
add (getCommandLinePrefix (commandLineUniqueID) + pipeName);
154 if (childProcess->start (args, streamFlags))
156 connection.reset (
new Connection (*
this, pipeName, timeoutMs <= 0 ? defaultTimeoutMs : timeoutMs));
158 if (connection->isConnected())
160 sendMessageToSlave ({ startMessage, specialMessageSize });
172 if (connection !=
nullptr)
174 sendMessageToSlave ({ killMessage, specialMessageSize });
175 connection->disconnect();
179 childProcess.reset();
191 connectToPipe (pipeName, timeoutMs);
203 void connectionMade()
override {}
207 void pingFailed()
override { connectionLost(); }
209 void messageReceived (
const MemoryBlock& m)
override 213 if (isMessageType (m, pingMessage))
216 if (isMessageType (m, killMessage))
217 return triggerConnectionLostMessage();
219 if (isMessageType (m, startMessage))
225 JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (
Connection)
237 if (connection !=
nullptr)
238 return connection->sendMessage (mb);
245 const String& commandLineUniqueID,
248 auto prefix = getCommandLinePrefix (commandLineUniqueID);
255 if (pipeName.isNotEmpty())
257 connection.reset (
new Connection (*
this, pipeName, timeoutMs <= 0 ? defaultTimeoutMs : timeoutMs));
259 if (! connection->isConnected())
264 return connection !=
nullptr;
size_t getSize() const noexcept
Returns the block's current allocated size, in bytes.
Acts as the slave end of a master/slave pair of connected processes.
ChildProcessSlave()
Creates a non-connected slave process.
bool stopThread(int timeOutMilliseconds)
Attempts to stop the thread running.
String fromFirstOccurrenceOf(StringRef substringToStartFrom, bool includeSubStringInResult, bool ignoreCase) const
Returns a section of the string starting from a given substring.
Acts as the master in a master/slave pair of connected processes.
Thread(const String &threadName, size_t threadStackSize=0)
Creates a thread.
void triggerAsyncUpdate()
Causes the callback to be triggered at a later time.
ChildProcessMaster()
Creates an uninitialised master process object.
virtual ~ChildProcessMaster()
Destructor.
Has a callback method that is triggered asynchronously.
A special array for holding a list of strings.
virtual void handleConnectionLost()
This will be called when the connection to the master process is lost.
virtual void handleConnectionLost()
This will be called when the slave process dies or is somehow disconnected.
virtual void handleConnectionMade()
This will be called when the master process finishes connecting to this slave.
bool launchSlaveProcess(const File &executableToLaunch, const String &commandLineUniqueID, int timeoutMs=0, int streamFlags=ChildProcess::wantStdOut|ChildProcess::wantStdErr)
Attempts to launch and connect to a slave process.
bool sendMessageToSlave(const MemoryBlock &)
Attempts to send a message to the slave process.
void killSlaveProcess()
Sends a kill message to the slave, and disconnects from it.
bool sendMessageToMaster(const MemoryBlock &)
Tries to send a message to the master process.
bool initialiseFromCommandLine(const String &commandLine, const String &commandLineUniqueID, int timeoutMs=0)
This checks some command-line parameters to see whether they were generated by ChildProcessMaster::la...
Launches and monitors a child process.
bool threadShouldExit() const
Checks whether the thread has been told to stop running.
static String toHexString(IntegerType number)
Returns a string representing this numeric value in hexadecimal.
Represents a local file or directory.
String upToFirstOccurrenceOf(StringRef substringToEndWith, bool includeSubStringInResult, bool ignoreCase) const
Returns the start of this string, up to the first occurrence of a substring.
virtual void handleMessageFromMaster(const MemoryBlock &)=0
This will be called to deliver messages from the master process.
virtual ~ChildProcessSlave()
Destructor.
A random number generator.
String trim() const
Returns a copy of this string with any whitespace characters removed from the start and end...
A class to hold a resizable block of raw data.
const String & getFullPathName() const noexcept
Returns the complete, absolute path of this file.
bool wait(int timeOutMilliseconds) const
Suspends the execution of this thread until either the specified timeout period has elapsed...
bool startsWith(StringRef text) const noexcept
Tests whether the string begins with another string.
void add(String stringToAdd)
Appends a string at the end of the array.
Manages a simple two-way messaging connection to another process, using either a socket or a named pi...
void startThread()
Starts the thread running.