- Library code update

- project update (added Eigen)

git-svn-id: http://moon:8086/svn/software/trunk/projects/mpsk_rx_gui@94 b431acfa-c32f-4a4a-93f1-934dc6c82436
This commit is contained in:
2014-12-20 20:59:48 +00:00
parent 1b4d8e9f54
commit dc5560392f
312 changed files with 6349 additions and 4195 deletions
@@ -25,12 +25,11 @@
class ActionBroadcaster::ActionMessage : public MessageManager::MessageBase
{
public:
ActionMessage (const ActionBroadcaster* const broadcaster_,
const String& messageText,
ActionListener* const listener_) noexcept
: broadcaster (const_cast <ActionBroadcaster*> (broadcaster_)),
ActionMessage (const ActionBroadcaster* ab,
const String& messageText, ActionListener* l) noexcept
: broadcaster (const_cast<ActionBroadcaster*> (ab)),
message (messageText),
listener (listener_)
listener (l)
{}
void messageCallback() override
@@ -61,7 +61,9 @@ AsyncUpdater::~AsyncUpdater()
void AsyncUpdater::triggerAsyncUpdate()
{
if (activeMessage->shouldDeliver.compareAndSetBool (1, 0))
activeMessage->post();
if (! activeMessage->post())
cancelPendingUpdate(); // if the message queue fails, this avoids getting
// trapped waiting for the message to arrive
}
void AsyncUpdater::cancelPendingUpdate() noexcept
@@ -68,8 +68,8 @@ public:
callback happens, this will cancel the handleAsyncUpdate() callback.
Note that this method simply cancels the next callback - if a callback is already
in progress on a different thread, this won't block until it finishes, so there's
no guarantee that the callback isn't still running when you return from
in progress on a different thread, this won't block until the callback finishes, so
there's no guarantee that the callback isn't still running when the method returns.
*/
void cancelPendingUpdate() noexcept;
@@ -27,7 +27,7 @@ enum { magicMastSlaveConnectionHeader = 0x712baf04 };
static const char* startMessage = "__ipc_st";
static const char* killMessage = "__ipc_k_";
static const char* pingMessage = "__ipc_p_";
enum { specialMessageSize = 8 };
enum { specialMessageSize = 8, defaultTimeoutMs = 8000 };
static String getCommandLinePrefix (const String& commandLineUniqueID)
{
@@ -40,7 +40,7 @@ static String getCommandLinePrefix (const String& commandLineUniqueID)
struct ChildProcessPingThread : public Thread,
private AsyncUpdater
{
ChildProcessPingThread() : Thread ("IPC ping"), timeoutMs (8000)
ChildProcessPingThread (int timeout) : Thread ("IPC ping"), timeoutMs (timeout)
{
pingReceived();
}
@@ -84,8 +84,10 @@ private:
struct ChildProcessMaster::Connection : public InterprocessConnection,
private ChildProcessPingThread
{
Connection (ChildProcessMaster& m, const String& pipeName)
: InterprocessConnection (false, magicMastSlaveConnectionHeader), owner (m)
Connection (ChildProcessMaster& m, const String& pipeName, int timeout)
: InterprocessConnection (false, magicMastSlaveConnectionHeader),
ChildProcessPingThread (timeout),
owner (m)
{
if (createPipe (pipeName, timeoutMs))
startThread (4);
@@ -140,7 +142,7 @@ bool ChildProcessMaster::sendMessageToSlave (const MemoryBlock& mb)
return false;
}
bool ChildProcessMaster::launchSlaveProcess (const File& executable, const String& commandLineUniqueID)
bool ChildProcessMaster::launchSlaveProcess (const File& executable, const String& commandLineUniqueID, int timeoutMs)
{
connection = nullptr;
jassert (childProcess.kill());
@@ -153,7 +155,7 @@ bool ChildProcessMaster::launchSlaveProcess (const File& executable, const Strin
if (childProcess.start (args))
{
connection = new Connection (*this, pipeName);
connection = new Connection (*this, pipeName, timeoutMs <= 0 ? defaultTimeoutMs : timeoutMs);
if (connection->isConnected())
{
@@ -171,8 +173,10 @@ bool ChildProcessMaster::launchSlaveProcess (const File& executable, const Strin
struct ChildProcessSlave::Connection : public InterprocessConnection,
private ChildProcessPingThread
{
Connection (ChildProcessSlave& p, const String& pipeName)
: InterprocessConnection (false, magicMastSlaveConnectionHeader), owner (p)
Connection (ChildProcessSlave& p, const String& pipeName, int timeout)
: InterprocessConnection (false, magicMastSlaveConnectionHeader),
ChildProcessPingThread (timeout),
owner (p)
{
connectToPipe (pipeName, timeoutMs);
startThread (4);
@@ -237,7 +241,8 @@ bool ChildProcessSlave::sendMessageToMaster (const MemoryBlock& mb)
}
bool ChildProcessSlave::initialiseFromCommandLine (const String& commandLine,
const String& commandLineUniqueID)
const String& commandLineUniqueID,
int timeoutMs)
{
String prefix (getCommandLinePrefix (commandLineUniqueID));
@@ -248,7 +253,7 @@ bool ChildProcessSlave::initialiseFromCommandLine (const String& commandLine,
if (pipeName.isNotEmpty())
{
connection = new Connection (*this, pipeName);
connection = new Connection (*this, pipeName, timeoutMs <= 0 ? defaultTimeoutMs : timeoutMs);
if (! connection->isConnected())
connection = nullptr;
@@ -64,10 +64,16 @@ public:
The commandLineUniqueID should be a short alphanumeric identifier (no spaces!)
that matches the string passed to ChildProcessMaster::launchSlaveProcess().
The timeoutMs parameter lets you specify how long the child process is allowed
to run without receiving a ping from the master before the master is considered to
have died, and handleConnectionLost() will be called. Passing <= 0 for this timeout
makes it use a default value.
Returns true if the command-line matches and the connection is made successfully.
*/
bool initialiseFromCommandLine (const String& commandLine,
const String& commandLineUniqueID);
const String& commandLineUniqueID,
int timeoutMs = 0);
//==============================================================================
/** This will be called to deliver messages from the master process.
@@ -141,11 +147,17 @@ public:
that gets launched must respond by calling ChildProcessSlave::initialiseFromCommandLine()
in its startup code, and must use a matching ID to commandLineUniqueID.
The timeoutMs parameter lets you specify how long the child process is allowed
to go without sending a ping before it is considered to have died and
handleConnectionLost() will be called. Passing <= 0 for this timeout makes
it use a default value.
If this all works, the method returns true, and you can begin sending and
receiving messages with the slave process.
*/
bool launchSlaveProcess (const File& executableToLaunch,
const String& commandLineUniqueID);
const String& commandLineUniqueID,
int timeoutMs = 0);
/** This will be called to deliver a message from the slave process.
The call will probably be made on a background thread, so be careful with your thread-safety!
@@ -31,7 +31,7 @@ struct InterprocessConnection::ConnectionThread : public Thread
private:
InterprocessConnection& owner;
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (ConnectionThread);
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (ConnectionThread)
};
//==============================================================================
@@ -69,11 +69,9 @@ bool InterprocessConnection::connectToSocket (const String& hostName,
thread->startThread();
return true;
}
else
{
socket = nullptr;
return false;
}
socket = nullptr;
return false;
}
bool InterprocessConnection::connectToPipe (const String& pipeName, const int timeoutMs)
@@ -143,41 +141,43 @@ bool InterprocessConnection::isConnected() const
String InterprocessConnection::getConnectedHostName() const
{
if (pipe != nullptr)
return "localhost";
if (socket != nullptr)
{
if (! socket->isLocal())
return socket->getHostName();
const ScopedLock sl (pipeAndSocketLock);
return "localhost";
if (pipe == nullptr && socket == nullptr)
return String();
if (socket != nullptr && ! socket->isLocal())
return socket->getHostName();
}
return String();
return IPAddress::local().toString();
}
//==============================================================================
bool InterprocessConnection::sendMessage (const MemoryBlock& message)
{
uint32 messageHeader[2];
messageHeader [0] = ByteOrder::swapIfBigEndian (magicMessageHeader);
messageHeader [1] = ByteOrder::swapIfBigEndian ((uint32) message.getSize());
uint32 messageHeader[2] = { ByteOrder::swapIfBigEndian (magicMessageHeader),
ByteOrder::swapIfBigEndian ((uint32) message.getSize()) };
MemoryBlock messageData (sizeof (messageHeader) + message.getSize());
messageData.copyFrom (messageHeader, 0, sizeof (messageHeader));
messageData.copyFrom (message.getData(), sizeof (messageHeader), message.getSize());
int bytesWritten = 0;
return writeData (messageData.getData(), (int) messageData.getSize()) == (int) messageData.getSize();
}
int InterprocessConnection::writeData (void* data, int dataSize)
{
const ScopedLock sl (pipeAndSocketLock);
if (socket != nullptr)
bytesWritten = socket->write (messageData.getData(), (int) messageData.getSize());
else if (pipe != nullptr)
bytesWritten = pipe->write (messageData.getData(), (int) messageData.getSize(), pipeReceiveMessageTimeout);
return socket->write (data, dataSize);
return bytesWritten == (int) messageData.getSize();
if (pipe != nullptr)
return pipe->write (data, dataSize, pipeReceiveMessageTimeout);
return 0;
}
//==============================================================================
@@ -201,6 +201,7 @@ private:
friend struct ContainerDeletePolicy<ConnectionThread>;
ScopedPointer<ConnectionThread> thread;
void runThread();
int writeData (void*, int);
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (InterprocessConnection)
};
@@ -1,7 +1,7 @@
{
"id": "juce_events",
"name": "JUCE message and event handling classes",
"version": "3.0.5",
"version": "3.0.8",
"description": "Classes for running an application's main event loop and sending/receiving messages, timers, etc.",
"website": "http://www.juce.com/juce",
"license": "GPL/Commercial",
@@ -138,7 +138,7 @@ String JUCEApplicationBase::getCommandLineParameters() { return String(
#else
#if JUCE_WINDOWS
#if JUCE_WINDOWS && ! defined (_CONSOLE)
String JUCE_CALLTYPE JUCEApplicationBase::getCommandLineParameters()
{
@@ -171,8 +171,13 @@ StringArray JUCE_CALLTYPE JUCEApplicationBase::getCommandLineParameterArray()
extern void initialiseNSApplication();
#endif
extern const char* const* juce_argv; // declared in juce_core
extern int juce_argc;
#if JUCE_WINDOWS
const char* const* juce_argv = nullptr;
int juce_argc = 0;
#else
extern const char* const* juce_argv; // declared in juce_core
extern int juce_argc;
#endif
String JUCEApplicationBase::getCommandLineParameters()
{
@@ -227,7 +232,7 @@ int JUCEApplicationBase::main()
jassert (app != nullptr);
if (! app->initialiseApp())
return 0;
return app->getApplicationReturnValue();
JUCE_TRY
{
@@ -50,24 +50,24 @@
MyJUCEApp() {}
~MyJUCEApp() {}
void initialise (const String& commandLine)
void initialise (const String& commandLine) override
{
myMainWindow = new MyApplicationWindow();
myMainWindow->setBounds (100, 100, 400, 500);
myMainWindow->setVisible (true);
}
void shutdown()
void shutdown() override
{
myMainWindow = nullptr;
}
const String getApplicationName()
const String getApplicationName() override
{
return "Super JUCE-o-matic";
}
const String getApplicationVersion()
const String getApplicationVersion() override
{
return "1.0";
}
@@ -55,13 +55,17 @@ JUCE_API void JUCE_CALLTYPE shutdownJuce_GUI();
/** A utility object that helps you initialise and shutdown Juce correctly
using an RAII pattern.
When an instance of this class is created, it calls initialiseJuce_GUI(),
and when it's deleted, it calls shutdownJuce_GUI(), which lets you easily
make sure that these functions are matched correctly.
When the first instance of this class is created, it calls initialiseJuce_GUI(),
and when the last instance is deleted, it calls shutdownJuce_GUI(), so that you
can easily be sure that as long as at least one instance of the class exists, the
library will be initialised.
This class is particularly handy to use at the beginning of a console app's
main() function, because it'll take care of shutting down whenever you return
from the main() call.
Be careful with your threading though - to be safe, you should always make sure
that these objects are created and deleted on the message thread.
*/
class JUCE_API ScopedJuceInitialiser_GUI
{
@@ -88,18 +92,12 @@ public:
juce::JUCEApplicationBase* juce_CreateApplication() { return new AppClass(); }
#else
#if JUCE_WINDOWS
#if defined (WINAPI) || defined (_WINDOWS_)
#define JUCE_MAIN_FUNCTION int __stdcall WinMain (HINSTANCE, HINSTANCE, const LPSTR, int)
#elif defined (_UNICODE)
#define JUCE_MAIN_FUNCTION int __stdcall WinMain (void*, void*, const wchar_t*, int)
#else
#define JUCE_MAIN_FUNCTION int __stdcall WinMain (void*, void*, const char*, int)
#endif
#define JUCE_MAIN_FUNCTION_ARGS
#if JUCE_WINDOWS && ! defined (_CONSOLE)
#define JUCE_MAIN_FUNCTION int __stdcall WinMain (struct HINSTANCE__*, struct HINSTANCE__*, char*, int)
#define JUCE_MAIN_FUNCTION_ARGS
#else
#define JUCE_MAIN_FUNCTION int main (int argc, char* argv[])
#define JUCE_MAIN_FUNCTION_ARGS argc, (const char**) argv
#define JUCE_MAIN_FUNCTION int main (int argc, char* argv[])
#define JUCE_MAIN_FUNCTION_ARGS argc, (const char**) argv
#endif
#define START_JUCE_APPLICATION(AppClass) \
@@ -66,12 +66,17 @@ void MessageManager::deleteInstance()
}
//==============================================================================
void MessageManager::MessageBase::post()
bool MessageManager::MessageBase::post()
{
MessageManager* const mm = MessageManager::instance;
if (mm == nullptr || mm->quitMessagePosted || ! postMessageToSystemQueue (this))
{
Ptr deleter (this); // (this will delete messages that were just created with a 0 ref count)
return false;
}
return true;
}
//==============================================================================
@@ -125,6 +130,25 @@ void MessageManager::stopDispatchLoop()
#endif
//==============================================================================
#if JUCE_COMPILER_SUPPORTS_LAMBDAS
struct AsyncFunction : private MessageManager::MessageBase
{
AsyncFunction (std::function<void(void)> f) : fn (f) { post(); }
private:
std::function<void(void)> fn;
void messageCallback() override { fn(); }
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (AsyncFunction)
};
void MessageManager::callAsync (std::function<void(void)> f)
{
new AsyncFunction (f);
}
#endif
//==============================================================================
class AsyncFunctionCallback : public MessageManager::MessageBase
{
@@ -158,9 +182,15 @@ void* MessageManager::callFunctionOnMessageThread (MessageCallbackFunction* cons
jassert (! currentThreadHasLockedMessageManager());
const ReferenceCountedObjectPtr<AsyncFunctionCallback> message (new AsyncFunctionCallback (func, parameter));
message->post();
message->finished.wait();
return message->result;
if (message->post())
{
message->finished.wait();
return message->result;
}
jassertfalse; // the OS message queue failed to send the message!
return nullptr;
}
//==============================================================================
@@ -275,7 +305,12 @@ bool MessageManagerLock::attemptLock (Thread* const threadToCheck, ThreadPoolJob
}
blockingMessage = new BlockingMessage();
blockingMessage->post();
if (! blockingMessage->post())
{
blockingMessage = nullptr;
return false;
}
while (! blockingMessage->lockedEvent.wait (20))
{
@@ -334,5 +369,7 @@ JUCE_API void JUCE_CALLTYPE shutdownJuce_GUI()
}
}
ScopedJuceInitialiser_GUI::ScopedJuceInitialiser_GUI() { initialiseJuce_GUI(); }
ScopedJuceInitialiser_GUI::~ScopedJuceInitialiser_GUI() { shutdownJuce_GUI(); }
static int numScopedInitInstances = 0;
ScopedJuceInitialiser_GUI::ScopedJuceInitialiser_GUI() { if (numScopedInitInstances++ == 0) initialiseJuce_GUI(); }
ScopedJuceInitialiser_GUI::~ScopedJuceInitialiser_GUI() { if (--numScopedInitInstances == 0) shutdownJuce_GUI(); }
@@ -91,6 +91,13 @@ public:
#endif
//==============================================================================
#if JUCE_COMPILER_SUPPORTS_LAMBDAS
/** Asynchronously invokes a function or C++11 lambda on the message thread.
Internally this uses the CallbackMessage class to invoke the callback.
*/
static void callAsync (std::function<void(void)>);
#endif
/** Calls a function using the message-thread.
This can be used by any thread to cause this function to be called-back
@@ -170,7 +177,7 @@ public:
virtual ~MessageBase() {}
virtual void messageCallback() = 0;
void post();
bool post();
typedef ReferenceCountedObjectPtr<MessageBase> Ptr;
@@ -100,7 +100,7 @@ bool MessageManager::dispatchNextMessageOnSystemQueue (const bool returnIfNoPend
using namespace WindowsMessageHelpers;
MSG m;
if (returnIfNoPendingMessages && ! PeekMessage (&m, (HWND) 0, 0, 0, 0))
if (returnIfNoPendingMessages && ! PeekMessage (&m, (HWND) 0, 0, 0, PM_NOREMOVE))
return false;
if (GetMessage (&m, (HWND) 0, 0, 0) >= 0)