Browse Source

Merge branch 'trac2198_5'

Mukund Sivaraman 12 years ago
parent
commit
4f3d61ec6d
49 changed files with 182 additions and 46 deletions
  1. 1 1
      src/bin/bind10/run_bind10.sh.in
  2. 1 1
      src/bin/bind10/tests/Makefile.am
  3. 1 1
      src/bin/bindctl/run_bindctl.sh.in
  4. 1 1
      src/bin/bindctl/tests/Makefile.am
  5. 1 1
      src/bin/cfgmgr/plugins/tests/Makefile.am
  6. 1 1
      src/bin/cfgmgr/tests/Makefile.am
  7. 1 1
      src/bin/cmdctl/run_b10-cmdctl.sh.in
  8. 1 1
      src/bin/cmdctl/tests/Makefile.am
  9. 1 1
      src/bin/dbutil/run_dbutil.sh.in
  10. 1 1
      src/bin/ddns/tests/Makefile.am
  11. 1 1
      src/bin/dhcp4/tests/Makefile.am
  12. 1 1
      src/bin/dhcp6/tests/Makefile.am
  13. 1 1
      src/bin/loadzone/run_loadzone.sh.in
  14. 1 1
      src/bin/loadzone/tests/Makefile.am
  15. 1 1
      src/bin/loadzone/tests/correct/Makefile.am
  16. 1 1
      src/bin/msgq/tests/Makefile.am
  17. 1 1
      src/bin/stats/tests/Makefile.am
  18. 1 1
      src/bin/tests/Makefile.am
  19. 1 1
      src/bin/xfrin/tests/Makefile.am
  20. 1 1
      src/bin/xfrout/tests/Makefile.am
  21. 1 1
      src/bin/zonemgr/tests/Makefile.am
  22. 1 1
      src/lib/dns/python/tests/Makefile.am
  23. 3 1
      src/lib/log/Makefile.am
  24. 5 1
      src/lib/log/logger_impl.cc
  25. 10 0
      src/lib/log/logger_manager.cc
  26. 6 0
      src/lib/log/logger_manager.h
  27. 8 0
      src/lib/log/tests/Makefile.am
  28. 11 0
      src/lib/log/tests/logger_lock_test.cc
  29. 1 0
      src/lib/log/tests/logger_lock_test.sh.in
  30. 1 1
      src/lib/python/isc/acl/tests/Makefile.am
  31. 1 1
      src/lib/python/isc/bind10/tests/Makefile.am
  32. 1 1
      src/lib/python/isc/cc/tests/Makefile.am
  33. 1 1
      src/lib/python/isc/config/tests/Makefile.am
  34. 1 1
      src/lib/python/isc/datasrc/tests/Makefile.am
  35. 1 1
      src/lib/python/isc/ddns/tests/Makefile.am
  36. 1 1
      src/lib/python/isc/log/tests/Makefile.am
  37. 1 1
      src/lib/python/isc/net/tests/Makefile.am
  38. 1 1
      src/lib/python/isc/notify/tests/Makefile.am
  39. 1 1
      src/lib/python/isc/server_common/tests/Makefile.am
  40. 1 1
      src/lib/python/isc/statistics/tests/Makefile.am
  41. 1 1
      src/lib/python/isc/sysinfo/tests/Makefile.am
  42. 1 1
      src/lib/python/isc/util/cio/tests/Makefile.am
  43. 1 1
      src/lib/python/isc/util/tests/Makefile.am
  44. 1 1
      src/lib/python/isc/xfrin/tests/Makefile.am
  45. 2 1
      src/lib/util/threads/Makefile.am
  46. 20 0
      src/lib/util/threads/sync.cc
  47. 40 5
      src/lib/util/threads/sync.h
  48. 38 0
      src/lib/util/threads/tests/lock_unittest.cc
  49. 1 1
      tests/lettuce/setup_intree_bind10.sh.in

File diff suppressed because it is too large
+ 1 - 1
src/bin/bind10/run_bind10.sh.in


File diff suppressed because it is too large
+ 1 - 1
src/bin/bind10/tests/Makefile.am


+ 1 - 1
src/bin/bindctl/run_bindctl.sh.in

@@ -27,7 +27,7 @@ export PYTHONPATH
 # required by loadable python modules.
 SET_ENV_LIBRARY_PATH=@SET_ENV_LIBRARY_PATH@
 if test $SET_ENV_LIBRARY_PATH = yes; then
-	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
+	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/threads/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
 	export @ENV_LIBRARY_PATH@
 fi
 

File diff suppressed because it is too large
+ 1 - 1
src/bin/bindctl/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/cfgmgr/plugins/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/cfgmgr/tests/Makefile.am


+ 1 - 1
src/bin/cmdctl/run_b10-cmdctl.sh.in

@@ -26,7 +26,7 @@ export PYTHONPATH
 # required by loadable python modules.
 SET_ENV_LIBRARY_PATH=@SET_ENV_LIBRARY_PATH@
 if test $SET_ENV_LIBRARY_PATH = yes; then
-        @ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
+        @ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/threads/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
         export @ENV_LIBRARY_PATH@
 fi
 

File diff suppressed because it is too large
+ 1 - 1
src/bin/cmdctl/tests/Makefile.am


+ 1 - 1
src/bin/dbutil/run_dbutil.sh.in

@@ -30,7 +30,7 @@ export PYTHONPATH
 # required by loadable python modules.
 SET_ENV_LIBRARY_PATH=@SET_ENV_LIBRARY_PATH@
 if test $SET_ENV_LIBRARY_PATH = yes; then
-	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
+	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/threads/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
 	export @ENV_LIBRARY_PATH@
 fi
 

File diff suppressed because it is too large
+ 1 - 1
src/bin/ddns/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/dhcp4/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/dhcp6/tests/Makefile.am


+ 1 - 1
src/bin/loadzone/run_loadzone.sh.in

@@ -25,7 +25,7 @@ export PYTHONPATH
 # required by loadable python modules.
 SET_ENV_LIBRARY_PATH=@SET_ENV_LIBRARY_PATH@
 if test $SET_ENV_LIBRARY_PATH = yes; then
-	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
+	@ENV_LIBRARY_PATH@=@abs_top_builddir@/src/lib/dns/.libs:@abs_top_builddir@/src/lib/dns/python/.libs:@abs_top_builddir@/src/lib/cryptolink/.libs:@abs_top_builddir@/src/lib/cc/.libs:@abs_top_builddir@/src/lib/config/.libs:@abs_top_builddir@/src/lib/log/.libs:@abs_top_builddir@/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/threads/.libs:@abs_top_builddir@/src/lib/util/io/.libs:@abs_top_builddir@/src/lib/exceptions/.libs:@abs_top_builddir@/src/lib/datasrc/.libs:$@ENV_LIBRARY_PATH@
 	export @ENV_LIBRARY_PATH@
 fi
 

File diff suppressed because it is too large
+ 1 - 1
src/bin/loadzone/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/loadzone/tests/correct/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/msgq/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/stats/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/xfrin/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/xfrout/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/bin/zonemgr/tests/Makefile.am


+ 1 - 1
src/lib/dns/python/tests/Makefile.am

@@ -28,7 +28,7 @@ EXTRA_DIST += testutil.py
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 3 - 1
src/lib/log/Makefile.am

@@ -48,5 +48,7 @@ if USE_CLANGPP
 libb10_log_la_CXXFLAGS += -Wno-error
 endif
 libb10_log_la_CPPFLAGS = $(AM_CPPFLAGS) $(LOG4CPLUS_INCLUDES)
-libb10_log_la_LIBADD   = $(top_builddir)/src/lib/util/libb10-util.la $(LOG4CPLUS_LIBS)
+libb10_log_la_LIBADD   = $(top_builddir)/src/lib/util/libb10-util.la
+libb10_log_la_LIBADD  += $(top_builddir)/src/lib/util/threads/libb10-threads.la
+libb10_log_la_LIBADD  += $(LOG4CPLUS_LIBS)
 libb10_log_la_LDFLAGS = -no-undefined -version-info 1:0:0

+ 5 - 1
src/lib/log/logger_impl.cc

@@ -29,6 +29,7 @@
 #include <log/logger_level.h>
 #include <log/logger_level_impl.h>
 #include <log/logger_name.h>
+#include <log/logger_manager.h>
 #include <log/message_dictionary.h>
 #include <log/message_types.h>
 
@@ -123,9 +124,12 @@ LoggerImpl::setInterprocessSync(isc::util::InterprocessSync* sync) {
 
 void
 LoggerImpl::outputRaw(const Severity& severity, const string& message) {
+    // Use a mutex locker for mutual exclusion from other threads in
+    // this process.
+    isc::util::thread::Mutex::Locker mutex_locker(LoggerManager::getMutex());
+
     // Use an interprocess sync locker for mutual exclusion from other
     // processes to avoid log messages getting interspersed.
-
     InterprocessSyncLocker locker(*sync_);
 
     if (!locker.lock()) {

+ 10 - 0
src/lib/log/logger_manager.cc

@@ -138,6 +138,9 @@ LoggerManager::init(const std::string& root, isc::log::Severity severity,
     if (file) {
         readLocalMessageFile(file);
     }
+
+    // Ensure that the mutex is constructed and ready at this point.
+    (void) getMutex();
 }
 
 
@@ -192,5 +195,12 @@ LoggerManager::reset() {
     LoggerManagerImpl::reset(initSeverity(), initDebugLevel());
 }
 
+isc::util::thread::Mutex&
+LoggerManager::getMutex() {
+    static isc::util::thread::Mutex mutex;
+
+    return (mutex);
+}
+
 } // namespace log
 } // namespace isc

+ 6 - 0
src/lib/log/logger_manager.h

@@ -16,6 +16,7 @@
 #define LOGGER_MANAGER_H
 
 #include "exceptions/exceptions.h"
+#include <util/threads/sync.h>
 #include <log/logger_specification.h>
 
 // Generated if, when updating the logging specification, an unknown
@@ -132,6 +133,11 @@ public:
     /// \param file Name of the local message file
     static void readLocalMessageFile(const char* file);
 
+    /// \brief Return a process-global mutex that's used for mutual
+    /// exclusion among threads of a single process during logging
+    /// calls.
+    static isc::util::thread::Mutex& getMutex();
+
 private:
     /// \brief Initialize Processing
     ///

+ 8 - 0
src/lib/log/tests/Makefile.am

@@ -71,6 +71,7 @@ AM_CPPFLAGS += $(GTEST_INCLUDES) $(LOG4CPLUS_INCLUDES)
 AM_LDFLAGS  += $(GTEST_LDFLAGS)
 
 AM_LDADD += $(top_builddir)/src/lib/util/libb10-util.la
+AM_LDADD += $(top_builddir)/src/lib/util/threads/libb10-threads.la
 AM_LDADD += $(top_builddir)/src/lib/log/libb10-log.la
 AM_LDADD += $(top_builddir)/src/lib/util/unittests/libutil_unittests.la
 AM_LDADD += $(top_builddir)/src/lib/exceptions/libb10-exceptions.la
@@ -131,6 +132,13 @@ endif
 # output needs to be compared with stored output (where "cut" and
 # "diff" are useful utilities).
 
+noinst_SCRIPTS  = console_test.sh
+noinst_SCRIPTS += destination_test.sh
+noinst_SCRIPTS += init_logger_test.sh
+noinst_SCRIPTS += local_file_test.sh
+noinst_SCRIPTS += logger_lock_test.sh
+noinst_SCRIPTS += severity_test.sh
+
 check-local:
 	$(SHELL) $(abs_builddir)/console_test.sh
 	$(SHELL) $(abs_builddir)/destination_test.sh

+ 11 - 0
src/lib/log/tests/logger_lock_test.cc

@@ -14,6 +14,7 @@
 
 #include <log/macros.h>
 #include <log/logger_support.h>
+#include <log/logger_manager.h>
 #include <log/log_messages.h>
 #include "util/interprocess_sync.h"
 #include "log_test_messages.h"
@@ -21,6 +22,7 @@
 
 using namespace std;
 using namespace isc::log;
+using isc::util::thread::Mutex;
 
 class MockLoggingSync : public isc::util::InterprocessSync {
 public:
@@ -31,6 +33,15 @@ public:
 
 protected:
     virtual bool lock() {
+        // We first check if the logger acquired a lock on the
+        // LoggerManager mutex.
+        try {
+            // This lock attempt is non-blocking.
+            Mutex::Locker locker(LoggerManager::getMutex(), false);
+        } catch (Mutex::Locker::AlreadyLocked& e) {
+            cout << "FIELD1 FIELD2 LOGGER_LOCK_TEST: MUTEXLOCK\n";
+        }
+
         cout << "FIELD1 FIELD2 LOGGER_LOCK_TEST: LOCK\n";
         return (true);
     }

+ 1 - 0
src/lib/log/tests/logger_lock_test.sh.in

@@ -31,6 +31,7 @@ passfail() {
 
 echo -n  "Testing that logger acquires and releases locks correctly:"
 cat > $tempfile << .
+LOGGER_LOCK_TEST: MUTEXLOCK
 LOGGER_LOCK_TEST: LOCK
 INFO  [bind10.log] LOG_LOCK_TEST_MESSAGE this is a test message.
 LOGGER_LOCK_TEST: UNLOCK

File diff suppressed because it is too large
+ 1 - 1
src/lib/python/isc/acl/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/lib/python/isc/bind10/tests/Makefile.am


+ 1 - 1
src/lib/python/isc/cc/tests/Makefile.am

@@ -10,7 +10,7 @@ EXTRA_DIST += test_session.py
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/config/tests/Makefile.am

@@ -8,7 +8,7 @@ EXTRA_DIST += unittest_fakesession.py
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/datasrc/tests/Makefile.am

@@ -22,7 +22,7 @@ CLEANFILES += $(abs_builddir)/zoneloadertest.sqlite3
 # of scope for this ticket
 LIBRARY_PATH_PLACEHOLDER = $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/datasrc/.libs:
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 else
 LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif

File diff suppressed because it is too large
+ 1 - 1
src/lib/python/isc/ddns/tests/Makefile.am


+ 1 - 1
src/lib/python/isc/log/tests/Makefile.am

@@ -8,7 +8,7 @@ EXTRA_DIST = console.out check_output.sh $(PYTESTS_NOGEN)
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/net/tests/Makefile.am

@@ -6,7 +6,7 @@ EXTRA_DIST = $(PYTESTS)
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/notify/tests/Makefile.am

@@ -11,7 +11,7 @@ EXTRA_DIST += testdata/multisoa.example
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 else
 # Some systems need the ds path even if not all paths are necessary
 LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/datasrc/.libs

+ 1 - 1
src/lib/python/isc/server_common/tests/Makefile.am

@@ -6,7 +6,7 @@ EXTRA_DIST = $(PYTESTS)
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/statistics/tests/Makefile.am

@@ -9,7 +9,7 @@ EXTRA_DIST += testdata/test_spec3.spec
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:@abs_top_builddir@/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 else
 # Some systems need the ds path even if not all paths are necessary
 LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/datasrc/.libs

File diff suppressed because it is too large
+ 1 - 1
src/lib/python/isc/sysinfo/tests/Makefile.am


File diff suppressed because it is too large
+ 1 - 1
src/lib/python/isc/util/cio/tests/Makefile.am


+ 1 - 1
src/lib/python/isc/util/tests/Makefile.am

@@ -7,7 +7,7 @@ EXTRA_DIST = $(PYTESTS)
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 1 - 1
src/lib/python/isc/xfrin/tests/Makefile.am

@@ -6,7 +6,7 @@ EXTRA_DIST = $(PYTESTS)
 # required by loadable python modules.
 LIBRARY_PATH_PLACEHOLDER =
 if SET_ENV_LIBRARY_PATH
-LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
+LIBRARY_PATH_PLACEHOLDER += $(ENV_LIBRARY_PATH)=$(abs_top_builddir)/src/lib/cryptolink/.libs:$(abs_top_builddir)/src/lib/dns/.libs:$(abs_top_builddir)/src/lib/dns/python/.libs:$(abs_top_builddir)/src/lib/cc/.libs:$(abs_top_builddir)/src/lib/config/.libs:$(abs_top_builddir)/src/lib/log/.libs:$(abs_top_builddir)/src/lib/util/.libs:$(abs_top_builddir)/src/lib/util/threads/.libs:$(abs_top_builddir)/src/lib/exceptions/.libs:$(abs_top_builddir)/src/lib/datasrc/.libs:$$$(ENV_LIBRARY_PATH)
 endif
 
 # test using command-line arguments, so use check-local target instead of TESTS

+ 2 - 1
src/lib/util/threads/Makefile.am

@@ -7,6 +7,7 @@ AM_CPPFLAGS += $(BOOST_INCLUDES) $(MULTITHREADING_FLAG)
 lib_LTLIBRARIES = libb10-threads.la
 libb10_threads_la_SOURCES  = sync.h sync.cc
 libb10_threads_la_SOURCES += thread.h thread.cc
-libb10_threads_la_LIBADD = $(top_builddir)/src/lib/exceptions/libb10-exceptions.la
+libb10_threads_la_LIBADD  = $(top_builddir)/src/lib/exceptions/libb10-exceptions.la
+libb10_threads_la_LIBADD += $(PTHREAD_LDFLAGS)
 
 CLEANFILES = *.gcno *.gcda

+ 20 - 0
src/lib/util/threads/sync.cc

@@ -169,6 +169,26 @@ Mutex::lock() {
 #endif // ENABLE_DEBUG
 }
 
+bool
+Mutex::tryLock() {
+    assert(impl_ != NULL);
+    const int result = pthread_mutex_trylock(&impl_->mutex);
+    // In the case of pthread_mutex_trylock(), if it is called on a
+    // locked mutex from the same thread, some platforms (such as fedora
+    // and debian) return EBUSY whereas others (such as centos 5) return
+    // EDEADLK. We return false and don't pass the lock attempt in both
+    // cases.
+    if (result == EBUSY || result == EDEADLK) {
+        return (false);
+    } else if (result != 0) {
+        isc_throw(isc::InvalidOperation, std::strerror(result));
+    }
+#ifdef ENABLE_DEBUG
+    postLockAction();           // Only in debug mode
+#endif // ENABLE_DEBUG
+    return (true);
+}
+
 void
 Mutex::unlock() {
     assert(impl_ != NULL);

+ 40 - 5
src/lib/util/threads/sync.h

@@ -15,6 +15,8 @@
 #ifndef B10_THREAD_SYNC_H
 #define B10_THREAD_SYNC_H
 
+#include <exceptions/exceptions.h>
+
 #include <boost/noncopyable.hpp>
 
 #include <cstdlib> // for NULL.
@@ -77,17 +79,34 @@ public:
     /// of function no matter by what means.
     class Locker : boost::noncopyable {
     public:
+        /// \brief Exception thrown when the mutex is already locked and
+        ///     a non-blocking locker is attempted around it.
+        struct AlreadyLocked : public isc::InvalidParameter {
+            AlreadyLocked(const char* file, size_t line, const char* what) :
+                isc::InvalidParameter(file, line, what)
+            {}
+        };
+
         /// \brief Constructor.
         ///
-        /// Locks the mutex. May block for extended period of time.
+        /// Locks the mutex. May block for extended period of time if
+        /// \c block is true.
         ///
         /// \throw isc::InvalidOperation when OS reports error. This usually
         ///     means an attempt to use the mutex in a wrong way (locking
         ///     a mutex second time from the same thread, for example).
-        Locker(Mutex& mutex) :
+        /// \throw AlreadyLocked if \c block is false and the mutex is
+        ///     already locked.
+        Locker(Mutex& mutex, bool block = true) :
             mutex_(mutex)
         {
-            mutex.lock();
+            if (block) {
+                mutex.lock();
+            } else {
+                if (!mutex.tryLock()) {
+                    isc_throw(AlreadyLocked, "The mutex is already locked");
+                }
+            }
         }
 
         /// \brief Destructor.
@@ -107,6 +126,24 @@ public:
     ///
     /// \todo Disable in non-debug build
     bool locked() const;
+
+private:
+    /// \brief Lock the mutex
+    ///
+    /// This method blocks until the mutex can be locked.
+    void lock();
+
+    /// \brief Try to lock the mutex
+    ///
+    /// This method doesn't block and returns immediately with a status
+    /// on whether the lock operation was successful.
+    ///
+    /// \return true if the lock was successful, false otherwise.
+    bool tryLock();
+
+    /// \brief Unlock the mutex
+    void unlock();
+
 private:
     friend class CondVar;
 
@@ -131,8 +168,6 @@ private:
 
     class Impl;
     Impl* impl_;
-    void lock();
-    void unlock();
 };
 
 /// \brief Encapsulation for a condition variable.

+ 38 - 0
src/lib/util/threads/tests/lock_unittest.cc

@@ -44,6 +44,44 @@ TEST(MutexTest, lockMultiple) {
         Mutex::Locker l2(mutex); // Attempt to lock again.
     }, isc::InvalidOperation);
     EXPECT_TRUE(mutex.locked()); // Debug-only build
+
+    // block=true explicitly.
+    Mutex mutex2;
+    EXPECT_FALSE(mutex2.locked()); // Debug-only build
+    Mutex::Locker l12(mutex2, true);
+    EXPECT_TRUE(mutex2.locked()); // Debug-only build
+}
+
+void
+testThread(Mutex* mutex)
+{
+    // block=false (tryLock).  This should not block indefinitely, but
+    // throw AlreadyLocked. If block were true, this would block
+    // indefinitely here.
+    EXPECT_THROW({
+        Mutex::Locker l3(*mutex, false);
+    }, Mutex::Locker::AlreadyLocked);
+
+    EXPECT_TRUE(mutex->locked()); // Debug-only build
+}
+
+// Test the non-blocking variant using a second thread.
+TEST(MutexTest, lockNonBlocking) {
+    // block=false (tryLock).
+    Mutex mutex;
+    Mutex::Locker l1(mutex, false);
+    EXPECT_TRUE(mutex.locked()); // Debug-only build
+
+    // First, try another locker from the same thread.
+    EXPECT_THROW({
+        Mutex::Locker l2(mutex, false);
+    }, Mutex::Locker::AlreadyLocked);
+
+    EXPECT_TRUE(mutex.locked()); // Debug-only build
+
+    // Now try another locker from a different thread.
+    Thread thread(boost::bind(&testThread, &mutex));
+    thread.wait();
 }
 
 #endif // ENABLE_DEBUG

File diff suppressed because it is too large
+ 1 - 1
tests/lettuce/setup_intree_bind10.sh.in