summaryrefslogtreecommitdiff
path: root/storage/xtradb/include/os0sync.h
diff options
context:
space:
mode:
authorSergei Golubchik <serg@mariadb.org>2016-06-21 15:27:09 +0200
committerSergei Golubchik <serg@mariadb.org>2016-06-21 15:27:09 +0200
commitb3f4cf7c1325ff1ca771a44ae25616d80605e8e7 (patch)
treedbd559f57db7ad20f9b9ecf1b4c2e143de32c986 /storage/xtradb/include/os0sync.h
parenta79d46c3a4839fa15c9f78dc2d5858ef948add18 (diff)
parentb42664e85e2cd512245de4fde94237a502fdbedb (diff)
downloadmariadb-git-b3f4cf7c1325ff1ca771a44ae25616d80605e8e7.tar.gz
Merge branch 'merge-xtradb-5.6' into 0.0
Diffstat (limited to 'storage/xtradb/include/os0sync.h')
-rw-r--r--storage/xtradb/include/os0sync.h128
1 files changed, 89 insertions, 39 deletions
diff --git a/storage/xtradb/include/os0sync.h b/storage/xtradb/include/os0sync.h
index db996b096bb..9bbb0bb7b5f 100644
--- a/storage/xtradb/include/os0sync.h
+++ b/storage/xtradb/include/os0sync.h
@@ -1,6 +1,6 @@
/*****************************************************************************
-Copyright (c) 1995, 2015, Oracle and/or its affiliates. All Rights Reserved.
+Copyright (c) 1995, 2016, Oracle and/or its affiliates. All Rights Reserved.
Copyright (c) 2008, Google Inc.
Portions of this file contain modifications contributed and copyrighted by
@@ -42,7 +42,6 @@ Created 9/6/1995 Heikki Tuuri
|| defined _M_X64 || defined __WIN__
#define IB_STRONG_MEMORY_MODEL
-#undef HAVE_IB_GCC_ATOMIC_TEST_AND_SET // Quick-and-dirty fix for bug 1519094
#endif /* __i386__ || __x86_64__ || _M_IX86 || _M_X64 || __WIN__ */
@@ -94,16 +93,62 @@ struct os_event {
#endif
os_fast_mutex_t os_mutex; /*!< this mutex protects the next
fields */
- ibool is_set; /*!< this is TRUE when the event is
- in the signaled state, i.e., a thread
- does not stop if it tries to wait for
- this event */
- ib_int64_t signal_count; /*!< this is incremented each time
- the event becomes signaled */
+private:
+ /** Masks for the event signal count and set flag in the count_and_set
+ field */
+ enum { count_mask = 0x7fffffffffffffffULL,
+ set_mask = 0x8000000000000000ULL};
+
+ /** The MSB is set whenever when the event is in the signaled state,
+ i.e. a thread does not stop if it tries to wait for this event. Lower
+ bits are incremented each time the event becomes signaled. */
+ ib_uint64_t count_and_set;
+public:
os_cond_t cond_var; /*!< condition variable is used in
waiting for the event */
- UT_LIST_NODE_T(os_event_t) os_event_list;
- /*!< list of all created events */
+
+ /** Initialise count_and_set field */
+ void init_count_and_set(void)
+ {
+ /* We return this value in os_event_reset(), which can then be
+ be used to pass to the os_event_wait_low(). The value of zero
+ is reserved in os_event_wait_low() for the case when the
+ caller does not want to pass any signal_count value. To
+ distinguish between the two cases we initialize signal_count
+ to 1 here. */
+ count_and_set = 1;
+ }
+
+ /** Mark this event as set */
+ void set(void)
+ {
+ count_and_set |= set_mask;
+ }
+
+ /** Unmark this event as set */
+ void reset(void)
+ {
+ count_and_set &= count_mask;
+ }
+
+ /** Return true if this event is set */
+ bool is_set(void) const
+ {
+ return count_and_set & set_mask;
+ }
+
+ /** Bump signal count for this event */
+ void inc_signal_count(void)
+ {
+ ut_ad(static_cast<ib_uint64_t>(signal_count()) < count_mask);
+ count_and_set++;
+ }
+
+ /** Return how many times this event has been signalled */
+ ib_int64_t signal_count(void) const
+ {
+ return (count_and_set & count_mask);
+ }
};
/** Denotes an infinite delay for os_event_wait_time() */
@@ -115,8 +160,7 @@ struct os_event {
/** Operating system mutex handle */
typedef struct os_mutex_t* os_ib_mutex_t;
-/** Mutex protecting counts and the event and OS 'slow' mutex lists */
-extern os_ib_mutex_t os_sync_mutex;
+// All the os_*_count variables are accessed atomically
/** This is incremented by 1 in os_thread_create and decremented by 1 in
os_thread_exit */
@@ -132,12 +176,15 @@ UNIV_INTERN
void
os_sync_init(void);
/*==============*/
-/*********************************************************//**
-Frees created events and OS 'slow' mutexes. */
+
+/** Create an event semaphore, i.e., a semaphore which may just have two
+states: signaled and nonsignaled. The created event is manual reset: it must be
+reset explicitly by calling sync_os_reset_event.
+@param[in,out] event memory block where to create the event */
UNIV_INTERN
void
-os_sync_free(void);
-/*==============*/
+os_event_create(os_event_t event);
+
/*********************************************************//**
Creates an event semaphore, i.e., a semaphore which may just have two states:
signaled and nonsignaled. The created event is manual reset: it must be reset
@@ -173,7 +220,10 @@ UNIV_INTERN
void
os_event_free(
/*==========*/
- os_event_t event); /*!< in: event to free */
+ os_event_t event, /*!< in: event to free */
+ bool free_memory = true);
+ /*!< in: if true, deallocate the event memory
+ block too */
/**********************************************************//**
Waits for an event object until it is in the signaled state.
@@ -467,28 +517,7 @@ amount to decrement. */
# define os_atomic_decrement_uint64(ptr, amount) \
os_atomic_decrement(ptr, amount)
-# if defined(HAVE_IB_GCC_ATOMIC_TEST_AND_SET)
-
-/** Do an atomic test-and-set.
-@param[in,out] ptr Memory location to set to non-zero
-@return the previous value */
-inline
-lock_word_t
-os_atomic_test_and_set(volatile lock_word_t* ptr)
-{
- return(__atomic_test_and_set(ptr, __ATOMIC_ACQUIRE));
-}
-
-/** Do an atomic clear.
-@param[in,out] ptr Memory location to set to zero */
-inline
-void
-os_atomic_clear(volatile lock_word_t* ptr)
-{
- __atomic_clear(ptr, __ATOMIC_RELEASE);
-}
-
-# elif defined(HAVE_ATOMIC_BUILTINS)
+# if defined(HAVE_ATOMIC_BUILTINS)
/** Do an atomic test and set.
@param[in,out] ptr Memory location to set to non-zero
@@ -517,6 +546,27 @@ os_atomic_clear(volatile lock_word_t* ptr)
return(__sync_lock_test_and_set(ptr, 0));
}
+# elif defined(HAVE_IB_GCC_ATOMIC_TEST_AND_SET)
+
+/** Do an atomic test-and-set.
+@param[in,out] ptr Memory location to set to non-zero
+@return the previous value */
+inline
+lock_word_t
+os_atomic_test_and_set(volatile lock_word_t* ptr)
+{
+ return(__atomic_test_and_set(ptr, __ATOMIC_ACQUIRE));
+}
+
+/** Do an atomic clear.
+@param[in,out] ptr Memory location to set to zero */
+inline
+void
+os_atomic_clear(volatile lock_word_t* ptr)
+{
+ __atomic_clear(ptr, __ATOMIC_RELEASE);
+}
+
# else
# error "Unsupported platform"