diff --git a/src/kits/app/Looper.cpp b/src/kits/app/Looper.cpp index 91c03156f9..72cd7a54b5 100644 --- a/src/kits/app/Looper.cpp +++ b/src/kits/app/Looper.cpp @@ -485,6 +485,14 @@ DBG(OUT("BLooper::Quit()\n")); printf("ERROR - you must Lock a looper before calling Quit(), " "team=%ld, looper=%s", Team(), name); } + + // Try to lock + if (!Lock()) + { + // We're toast already + return; + } + DBG(OUT(" is locked\n")); if (!fRunCalled || find_thread(NULL) == fTaskID) @@ -734,7 +742,16 @@ status_t BLooper::GetSupportedSuites(BMessage* data) //------------------------------------------------------------------------------ void BLooper::AddCommonFilter(BMessageFilter* filter) { - AssertLocked(); + if (!filter) + { + return; + } + + if (!Locked()) + { + debugger("Owning Looper must be locked before calling AddCommonFilter"); + } + if (!fCommonFilters) { fCommonFilters = new BList(FILTER_LIST_BLOCK_SIZE); diff --git a/src/tests/kits/app/Jamfile b/src/tests/kits/app/Jamfile index 69d89f6188..ded6ad5881 100644 --- a/src/tests/kits/app/Jamfile +++ b/src/tests/kits/app/Jamfile @@ -34,6 +34,8 @@ CommonTestLib libapptest.so RemoveHandlerTest.cpp PerformTest.cpp RunTest.cpp + LooperForThreadTest.cpp + AddCommonFilterTest.cpp # BMessageQueue MessageQueueTest.cpp diff --git a/src/tests/kits/app/blooper/AddCommonFilterTest.cpp b/src/tests/kits/app/blooper/AddCommonFilterTest.cpp new file mode 100644 index 0000000000..d97967605f --- /dev/null +++ b/src/tests/kits/app/blooper/AddCommonFilterTest.cpp @@ -0,0 +1,105 @@ +//------------------------------------------------------------------------------ +// AddCommonFilterTest.cpp +// +//------------------------------------------------------------------------------ + +// Standard Includes ----------------------------------------------------------- + +// System Includes ------------------------------------------------------------- +#include +#include + +// Project Includes ------------------------------------------------------------ + +// Local Includes -------------------------------------------------------------- +#include "AddCommonFilterTest.h" + +// Local Defines --------------------------------------------------------------- + +// Globals --------------------------------------------------------------------- + +//------------------------------------------------------------------------------ +/** + AddCommonFilter(BMessageFilter* filter) + @case NULL filter + @param filter is NULL + @results none + @note R5 chokes on this test; doesn't param check, apparently. + */ +void TAddCommonFilterTest::AddCommonFilterTest1() +{ +#ifndef TEST_R5 + BLooper Looper; + Looper.AddCommonFilter(NULL); +#endif +} +//------------------------------------------------------------------------------ +/** + AddCommonFilter(BMessageFilter* filter) + @case Valid filter, looper not locked + @param Valid BMessageFilter pointer + @results Debugger message "Owning Looper must be locked before calling + AddCommonFilter" + */ +void TAddCommonFilterTest::AddCommonFilterTest2() +{ + BLooper Looper; + Looper.Unlock(); + BMessageFilter* Filter = new BMessageFilter('1234'); + Looper.AddCommonFilter(&Filter); +} +//------------------------------------------------------------------------------ +/** + AddCommonFilter(BMessageFilter* filter) + @case Valid filter, looper locked + @param Valid BMessageFilter pointer + @results + */ +void TAddCommonFilterTest::AddCommonFilterTest3() +{ + BLooper Looper; + BMessageFilter* Filter = new BMessageFilter('1234'); + Looper.AddCommonFilter(&Filter); +} +//------------------------------------------------------------------------------ +/** + AddCommonFilter(BMessageFilter* filter) + @case Valid filter, looper locked, owned by another looper + @param Valid BMessageFilter pointer + @results + */ +void TAddCommonFilterTest::AddCommonFilterTest4() +{ + BLooper Looper1; + BLooper Looper2; + BMessageFilter* Filter = new BMessageFilter('1234'); + Looper1.AddCommonFilter(&Filter); + Looper2.AddCommonFilter(&Filter); +} +//------------------------------------------------------------------------------ +#ifdef ADD_TEST +#undef ADD_TEST +#endif +#define ADD_TEST(__test_name__) \ + ADD_TEST4(BLooper, suite, TAddCommonFilterTest, __test_name__); +TestSuite* TAddCommonFilterTest::Suite() +{ + TestSuite* suite = + new TestSuite("BLooper::AddCommonFilter(BMessageFilter*)"); + + ADD_TEST(AddCommonFilterTest1); + ADD_TEST(AddCommonFilterTest2); + ADD_TEST(AddCommonFilterTest3); + ADD_TEST(AddCommonFilterTest4); + + return suite; +} +//------------------------------------------------------------------------------ + +/* + * $Log $ + * + * $Id $ + * + */ + diff --git a/src/tests/kits/app/blooper/AddCommonFilterTest.h b/src/tests/kits/app/blooper/AddCommonFilterTest.h new file mode 100644 index 0000000000..5fa59b51ea --- /dev/null +++ b/src/tests/kits/app/blooper/AddCommonFilterTest.h @@ -0,0 +1,44 @@ +//------------------------------------------------------------------------------ +// AddCommonFilterTest.h +// +//------------------------------------------------------------------------------ + +#ifndef ADDCOMMONFILTERTEST_H +#define ADDCOMMONFILTERTEST_H + +// Standard Includes ----------------------------------------------------------- + +// System Includes ------------------------------------------------------------- + +// Project Includes ------------------------------------------------------------ + +// Local Includes -------------------------------------------------------------- +#include "../common.h" + +// Local Defines --------------------------------------------------------------- + +// Globals --------------------------------------------------------------------- + +class TAddCommonFilterTest : public TestCase +{ + public: + TAddCommonFilterTest() {;} + TAddCommonFilterTest(std::string name) : TestCase(name) {;} + + void AddCommonFilterTest1(); + void AddCommonFilterTest2(); + void AddCommonFilterTest3(); + void AddCommonFilterTest4(); + + static TestSuite* Suite(); +}; + +#endif //ADDCOMMONFILTERTEST_H + +/* + * $Log $ + * + * $Id $ + * + */ + diff --git a/src/tests/kits/app/blooper/BLooperCases b/src/tests/kits/app/blooper/BLooperCases index b16bfa6d66..defe17796d 100644 --- a/src/tests/kits/app/blooper/BLooperCases +++ b/src/tests/kits/app/blooper/BLooperCases @@ -69,14 +69,20 @@ case 4: handler is valid, one of many added and removed case 5: handler is valid, looper is unlocked PreferredHandler() const; +-------------- SetPreferredHandler(BHandler* handler); +-------------- Run(); -------------- case 1: Attempt to call Run() twice +case 2: Check Thread() against return of Run() +case 3: Delete looper after calling Run() Quit() -------------- +case : Call Quit() on unlocked BLooper + QuitRequested() -------------- Lock() @@ -91,8 +97,12 @@ Thread() const -------------- Team() const -------------- + LooperForThread(thread_id tid) -------------- +case 1: tid is valid +case 2: tid is not valid + LockingThread() const -------------- CountLocks() const @@ -105,14 +115,31 @@ ResolveSpecifier(BMessage* msg, int32 index, BMessage* specifier, int32 form, co -------------- GetSupportedSuites(BMessage* data) -------------- + AddCommonFilter(BMessageFilter* filter) -------------- +case : NULL filter +case : Valid filter, looper not locked +case : Valid filter, looper locked +case : Valid filter, looper locked, owned by another looper + RemoveCommonFilter(BMessageFilter* filter) -------------- +case : NULL filter +case : Valid filter, looper not locked +case : Valid filter, not owned by looper +case : Valid filter, owned by looper + SetCommonFilterList(BList* filters) -------------- +case : NULL list +case : Valid list, looper not locked +case : Valid list, looper locked +case : Valid list, looper locked, owned by another looper + CommonFilterList() const -------------- +case : Default constructed BLooper Perform(perform_code d, void* arg) -------------- diff --git a/src/tests/kits/app/blooper/LooperForThreadTest.cpp b/src/tests/kits/app/blooper/LooperForThreadTest.cpp new file mode 100644 index 0000000000..0b781b1657 --- /dev/null +++ b/src/tests/kits/app/blooper/LooperForThreadTest.cpp @@ -0,0 +1,65 @@ +//------------------------------------------------------------------------------ +// LooperForThreadTest.cpp +// +//------------------------------------------------------------------------------ + +// Standard Includes ----------------------------------------------------------- + +// System Includes ------------------------------------------------------------- +#include + +// Project Includes ------------------------------------------------------------ + +// Local Includes -------------------------------------------------------------- +#include "LooperForThreadTest.h" + +// Local Defines --------------------------------------------------------------- + +// Globals --------------------------------------------------------------------- + +//------------------------------------------------------------------------------ +/** + LooperForThread(thread_id) + @case tid is valid + */ +void TLooperForThreadTest::LooperForThreadTest1() +{ + BLooper* Looper = new BLooper; + thread_id tid = Looper->Run(); + CPPUNIT_ASSERT(Looper == BLooper::LooperForThread(tid)); + Looper->Lock(); + Looper->Quit(); +} +//------------------------------------------------------------------------------ +/** + LooperForThread(thread_id) + @case tid is not valid + */ +void TLooperForThreadTest::LooperForThreadTest2() +{ + CPPUNIT_ASSERT(BLooper::LooperForThread(find_thread(NULL)) == NULL); +} +//------------------------------------------------------------------------------ +#ifdef ADD_TEST +#undef ADD_TEST +#endif +#define ADD_TEST(__test_name__) \ + ADD_TEST4(BLooper, suite, TLooperForThreadTest, __test_name__) +TestSuite* TLooperForThreadTest::Suite() +{ + TestSuite* suite = new TestSuite("BLooper::LooperForTest(thread_id)"); + + ADD_TEST(LooperForThreadTest1); + ADD_TEST(LooperForThreadTest2); + + return suite; +} +//------------------------------------------------------------------------------ + +/* + * $Log $ + * + * $Id $ + * + */ + diff --git a/src/tests/kits/app/blooper/LooperForThreadTest.h b/src/tests/kits/app/blooper/LooperForThreadTest.h new file mode 100644 index 0000000000..9e885cf6ba --- /dev/null +++ b/src/tests/kits/app/blooper/LooperForThreadTest.h @@ -0,0 +1,42 @@ +//------------------------------------------------------------------------------ +// LooperForThreadTest.h +// +//------------------------------------------------------------------------------ + +#ifndef LOOPERFORTHREADTEST_H +#define LOOPERFORTHREADTEST_H + +// Standard Includes ----------------------------------------------------------- + +// System Includes ------------------------------------------------------------- + +// Project Includes ------------------------------------------------------------ + +// Local Includes -------------------------------------------------------------- +#include "../common.h" + +// Local Defines --------------------------------------------------------------- + +// Globals --------------------------------------------------------------------- + +class TLooperForThreadTest : public TestCase +{ + public: + TLooperForThreadTest() {;} + TLooperForThreadTest(std::string name) : TestCase(name) {;} + + void LooperForThreadTest1(); + void LooperForThreadTest2(); + + static TestSuite* Suite(); +}; + +#endif //LOOPERFORTHREADTEST_H + +/* + * $Log $ + * + * $Id $ + * + */ + diff --git a/src/tests/kits/app/blooper/LooperTest.cpp b/src/tests/kits/app/blooper/LooperTest.cpp index f2ed6eb058..cb672387c2 100644 --- a/src/tests/kits/app/blooper/LooperTest.cpp +++ b/src/tests/kits/app/blooper/LooperTest.cpp @@ -8,6 +8,8 @@ #include "AddHandlerTest.h" #include "PerformTest.h" #include "RunTest.h" +#include "LooperForThreadTest.h" +#include "AddCommonFilterTest.h" Test* LooperTestSuite() { @@ -21,6 +23,8 @@ Test* LooperTestSuite() tests->addTest(TAddHandlerTest::Suite()); tests->addTest(TPerformTest::Suite()); tests->addTest(TRunTest::Suite()); + tests->addTest(TLooperForThreadTest::Suite()); + tests->addTest(TAddCommonFilterTest::Suite()); return tests; } diff --git a/src/tests/kits/app/blooper/RunTest.cpp b/src/tests/kits/app/blooper/RunTest.cpp index f131f86d35..ed09f75bee 100644 --- a/src/tests/kits/app/blooper/RunTest.cpp +++ b/src/tests/kits/app/blooper/RunTest.cpp @@ -21,20 +21,57 @@ /** Run() @case Attempt to call Run() twice - @results + @results debugger message "can't call BLooper::Run twice!" */ void TRunTest::RunTest1() { + DEBUGGER_ESCAPE; + BLooper Looper; Looper.Run(); Looper.Run(); + Looper.Quit(); } //------------------------------------------------------------------------------ +/** + Run() + @case Check thread_id of Looper + @results Run() and Thread() return the same thread_id + */ +void TRunTest::RunTest2() +{ + BLooper* Looper = new BLooper; + thread_id tid = Looper->Run(); + CPPUNIT_ASSERT(tid == Looper->Thread()); + Looper->Lock(); + Looper->Quit(); +} +//------------------------------------------------------------------------------ +/** + Run() + @case Delete looper after calling Run() + @results Debugger message "You can't call delete on a BLooper object + once it is running." + */ +void TRunTest::RunTest3() +{ + BLooper* Looper = new BLooper; + Looper->Run(); + delete Looper; +} +//------------------------------------------------------------------------------ +#ifdef ADD_TEST +#undef ADD_TEST +#endif +#define ADD_TEST(__test_name__) \ + ADD_TEST4(BLooper, suite, TRunTest, __test_name__) + TestSuite* TRunTest::Suite() { TestSuite* suite = new TestSuite("BLooper::Run()"); - ADD_TEST(suite, TRunTest, RunTest1); + ADD_TEST(RunTest1); + ADD_TEST(RunTest2); return suite; } diff --git a/src/tests/kits/app/blooper/RunTest.h b/src/tests/kits/app/blooper/RunTest.h index de4e7d7718..5f24338484 100644 --- a/src/tests/kits/app/blooper/RunTest.h +++ b/src/tests/kits/app/blooper/RunTest.h @@ -26,6 +26,8 @@ class TRunTest : public TestCase TRunTest(std::string name) : TestCase(name) {;} void RunTest1(); + void RunTest2(); + void RunTest3(); static TestSuite* Suite(); };