Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
FORMUS3IC_LAS3
/
embb
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Members
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit
3926d7a1
authored
Nov 02, 2016
by
Marcus Winter
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
full implementation of threading analysis mode
parent
8aa76fe9
Hide whitespace changes
Inline
Side-by-side
Showing
47 changed files
with
351 additions
and
142 deletions
+351
-142
algorithms_cpp/test/main.cc
+0
-4
base_c/include/embb/base/c/atomic.h
+19
-4
base_c/include/embb/base/c/internal/atomic/and_assign.h
+3
-2
base_c/include/embb/base/c/internal/atomic/atomic_variables.h
+2
-12
base_c/include/embb/base/c/internal/atomic/compare_and_swap.h
+5
-3
base_c/include/embb/base/c/internal/atomic/destroy.h
+57
-0
base_c/include/embb/base/c/internal/atomic/fetch_and_add.h
+3
-5
base_c/include/embb/base/c/internal/atomic/init.h
+57
-0
base_c/include/embb/base/c/internal/atomic/load.h
+4
-3
base_c/include/embb/base/c/internal/atomic/or_assign.h
+3
-2
base_c/include/embb/base/c/internal/atomic/store.h
+3
-2
base_c/include/embb/base/c/internal/atomic/swap.h
+3
-2
base_c/include/embb/base/c/internal/atomic/xor_assign.h
+3
-2
base_c/src/atomic.c
+0
-14
base_c/src/counter.c
+2
-1
base_c/src/internal/thread_index.c
+12
-12
base_c/src/memory_allocation.c
+6
-6
base_c/src/mutex.c
+2
-3
base_c/test/main.cc
+0
-4
base_c/test/thread_index_test.cc
+11
-2
base_c/test/thread_index_test.h
+6
-1
base_cpp/include/embb/base/internal/atomic/atomic_arithmetic.h
+2
-0
base_cpp/include/embb/base/internal/atomic/atomic_base.h
+28
-4
base_cpp/include/embb/base/internal/atomic/atomic_integer.h
+6
-0
base_cpp/include/embb/base/internal/atomic/atomic_pointer.h
+4
-4
base_cpp/test/main.cc
+0
-4
containers_cpp/test/main.cc
+0
-4
dataflow_cpp/include/embb/dataflow/internal/inputs.h
+20
-5
dataflow_cpp/include/embb/dataflow/network.h
+4
-1
dataflow_cpp/test/main.cc
+0
-4
mtapi_c/src/embb_mtapi_action_plugin_t.c
+2
-0
mtapi_c/src/embb_mtapi_action_t.c
+17
-3
mtapi_c/src/embb_mtapi_alloc.c
+4
-4
mtapi_c/src/embb_mtapi_group_t.c
+9
-3
mtapi_c/src/embb_mtapi_node_t.c
+3
-0
mtapi_c/src/embb_mtapi_pool_template-inl.h
+0
-3
mtapi_c/src/embb_mtapi_queue_t.c
+6
-0
mtapi_c/src/embb_mtapi_scheduler_t.c
+3
-0
mtapi_c/src/embb_mtapi_task_t.c
+12
-1
mtapi_c/src/embb_mtapi_thread_context_t.c
+8
-1
mtapi_c/test/embb_mtapi_test_error.cc
+4
-0
mtapi_c/test/embb_mtapi_test_plugin.cc
+5
-0
mtapi_c/test/main.cc
+0
-4
mtapi_cpp/test/main.cc
+0
-4
mtapi_plugins_c/mtapi_network_c/src/embb_mtapi_network.c
+13
-1
mtapi_plugins_c/mtapi_network_c/test/main.cc
+0
-4
mtapi_plugins_c/mtapi_opencl_c/test/main.cc
+0
-4
No files found.
algorithms_cpp/test/main.cc
View file @
3926d7a1
...
...
@@ -68,8 +68,6 @@ int compute1_() {
}
PT_MAIN
(
"Algorithms"
)
{
embb_atomic_initialize
();
embb
::
mtapi
::
Node
::
Initialize
(
THIS_DOMAIN_ID
,
THIS_NODE_ID
);
PT_RUN
(
PartitionerTest
);
...
...
@@ -85,6 +83,4 @@ PT_MAIN("Algorithms") {
embb
::
mtapi
::
Node
::
Finalize
();
PT_EXPECT
(
embb_get_bytes_allocated
()
==
0
);
embb_atomic_finalize
();
}
base_c/include/embb/base/c/atomic.h
View file @
3926d7a1
...
...
@@ -295,6 +295,12 @@ extern "C" {
#include <embb/base/c/internal/cmake_config.h>
#ifdef EMBB_THREADING_ANALYSIS_MODE
#include <embb/base/c/internal/platform.h>
#include <assert.h>
int
embb_mutex_init
(
embb_mutex_t
*
mutex
,
int
type
);
int
embb_mutex_lock
(
embb_mutex_t
*
mutex
...
...
@@ -304,13 +310,20 @@ int embb_mutex_unlock(
embb_mutex_t
*
mutex
);
#define EMBB_ATOMIC_MUTEX_LOCK embb_mutex_lock(&embb_atomic_mutex)
#define EMBB_ATOMIC_MUTEX_UNLOCK embb_mutex_unlock(&embb_atomic_mutex)
void
embb_mutex_destroy
(
embb_mutex_t
*
mutex
);
#define EMBB_ATOMIC_MUTEX_INIT(mutex) embb_mutex_init(&(mutex), 0)
#define EMBB_ATOMIC_MUTEX_LOCK(mutex) embb_mutex_lock(&(mutex))
#define EMBB_ATOMIC_MUTEX_UNLOCK(mutex) embb_mutex_unlock(&(mutex))
#define EMBB_ATOMIC_MUTEX_DESTROY(mutex) embb_mutex_destroy(&(mutex))
#define EMBB_ATOMIC_INIT_CHECK(variable) assert(variable->marker == 0x12345678)
#else
#define EMBB_ATOMIC_MUTEX_LOCK
#define EMBB_ATOMIC_MUTEX_UNLOCK
#define EMBB_ATOMIC_MUTEX_LOCK
(mutex)
#define EMBB_ATOMIC_MUTEX_UNLOCK
(mutex)
#endif
...
...
@@ -318,6 +331,8 @@ int embb_mutex_unlock(
#include <embb/base/c/internal/atomic/atomic_sizes.h>
#include <embb/base/c/internal/atomic/atomic_variables.h>
#include <embb/base/c/internal/macro_helper.h>
#include <embb/base/c/internal/atomic/init.h>
#include <embb/base/c/internal/atomic/destroy.h>
#include <embb/base/c/internal/atomic/load.h>
#include <embb/base/c/internal/atomic/and_assign.h>
#include <embb/base/c/internal/atomic/store.h>
...
...
base_c/include/embb/base/c/internal/atomic/and_assign.h
View file @
3926d7a1
...
...
@@ -69,12 +69,10 @@
#define EMBB_DEFINE_AND_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX)\
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_and_assign_, \
EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
EMBB_ATOMIC_MUTEX_LOCK; \
__asm__ __volatile__("lock and" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (value) \
: \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
}
#else
#error "No atomic fetch and store implementation found"
...
...
@@ -154,8 +152,11 @@ EMBB_DEFINE_AND_ASSIGN(4, "")
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun;\
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE));\
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(embb_internal__atomic_and_assign_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *) \
(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
...
...
base_c/include/embb/base/c/internal/atomic/atomic_variables.h
View file @
3926d7a1
...
...
@@ -41,6 +41,8 @@
typedef struct \
{ \
volatile EMBB_ATOMIC_PARAMETER_TYPE_NATIVE internal_variable; \
embb_mutex_t internal_mutex; \
uint32_t marker; \
} EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX);
EMBB_ATOMIC_INTERNAL_DEFINE_VARIABLE
(
char
,
char
)
...
...
@@ -58,16 +60,4 @@ EMBB_ATOMIC_INTERNAL_DEFINE_VARIABLE(size_t, size_t)
EMBB_ATOMIC_INTERNAL_DEFINE_VARIABLE
(
ptrdiff_t
,
ptrdiff_t
)
EMBB_ATOMIC_INTERNAL_DEFINE_VARIABLE
(
uintmax_t
,
uintmax_t
)
#ifdef EMBB_THREADING_ANALYSIS_MODE
#include <embb/base/c/mutex.h>
extern
embb_mutex_t
embb_atomic_mutex
;
void
embb_atomic_initialize
();
void
embb_atomic_finalize
();
#else
#define embb_atomic_initialize()
#define embb_atomic_finalize()
#endif
#endif //EMBB_BASE_C_INTERNAL_ATOMIC_ATOMIC_VARIABLES_H_
base_c/include/embb/base/c/internal/atomic/compare_and_swap.h
View file @
3926d7a1
...
...
@@ -58,7 +58,6 @@
EMBB_PLATFORM_INLINE int EMBB_CAT2(embb_internal__atomic_compare_and_swap_, \
EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* expected, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) desired) { \
EMBB_ATOMIC_MUTEX_LOCK; \
char result; \
__asm__ __volatile__ ("lock cmpxchg" EMBB_ATOMIC_X86_SIZE_SUFFIX\
" %3, %0 \n\t" \
...
...
@@ -66,7 +65,6 @@
: "+m" (*pointer_to_value), "+a" (*expected), "=q" (result) \
: "q" (desired) \
: "memory", "cc" ); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
return result; \
}
#else
...
...
@@ -140,8 +138,12 @@ EMBB_DEFINE_COMPARE_AND_SWAP(4, "")
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE* expected, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE desired) {\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) desired_pun;\
memcpy(&desired_pun, &desired, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE));\
return EMBB_CAT2(embb_internal__atomic_compare_and_swap_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *) \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
int result = EMBB_CAT2(embb_internal__atomic_compare_and_swap_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *) \
(&(variable->internal_variable)), (EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *) expected, desired_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
return result;\
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
...
...
base_c/include/embb/base/c/internal/atomic/destroy.h
0 → 100644
View file @
3926d7a1
/*
* Copyright (c) 2014-2016, Siemens AG. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef EMBB_BASE_C_INTERNAL_ATOMIC_DESTROY_H_
#define EMBB_BASE_C_INTERNAL_ATOMIC_DESTROY_H_
#ifndef DOXYGEN
#include <embb/base/c/internal/config.h>
#include <embb/base/c/internal/atomic/atomic_sizes.h>
#include <embb/base/c/internal/macro_helper.h>
#include <embb/base/c/internal/atomic/atomic_variables.h>
#include <string.h>
/*
* See file and_assign.h for a detailed (and operation independent) description
* of the following macro.
*/
#define EMBB_ATOMIC_INTERNAL_DEFINE_DESTROY_METHOD(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) \
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_atomic_destroy_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)(\
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable) { \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_DESTROY(variable->internal_mutex); \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
#define EMBB_ATOMIC_METHOD_TO_GENERATE DESTROY_METHOD
#include <embb/base/c/internal/atomic/generate_atomic_implementation_template.h>
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
#endif //DOXYGEN
#endif //EMBB_BASE_C_INTERNAL_ATOMIC_INIT_H_
base_c/include/embb/base/c/internal/atomic/fetch_and_add.h
View file @
3926d7a1
...
...
@@ -57,12 +57,10 @@
#define EMBB_DEFINE_FETCH_AND_ADD(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) EMBB_CAT2(embb_internal__atomic_fetch_and_add_, EMBB_PARAMETER_SIZE_BYTE) \
(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value) { \
EMBB_ATOMIC_MUTEX_LOCK; \
__asm__ __volatile__ ("lock xadd" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (new_value) \
: \
: "memory", "cc" ); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
return new_value; \
}
#else
...
...
@@ -109,9 +107,6 @@ EMBB_DEFINE_FETCH_AND_ADD(8, "q")
: "memory", "cc" ); \
return result; \
}
/* return __sync_fetch_and_add( \
pointer_to_value, new_value); \
}*/
#else
#error "No atomic fetch and store implementation found"
#endif
...
...
@@ -133,9 +128,12 @@ EMBB_DEFINE_FETCH_AND_ADD(4, "")
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun; \
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) return_val = EMBB_CAT2(embb_internal__atomic_fetch_and_add_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)(\
(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)\
(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
EMBB_ATOMIC_PARAMETER_TYPE_NATIVE return_val_pun; \
memcpy(&return_val_pun, &return_val, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
return return_val_pun; \
...
...
base_c/include/embb/base/c/internal/atomic/init.h
0 → 100644
View file @
3926d7a1
/*
* Copyright (c) 2014-2016, Siemens AG. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef EMBB_BASE_C_INTERNAL_ATOMIC_INIT_H_
#define EMBB_BASE_C_INTERNAL_ATOMIC_INIT_H_
#ifndef DOXYGEN
#include <embb/base/c/internal/config.h>
#include <embb/base/c/internal/atomic/atomic_sizes.h>
#include <embb/base/c/internal/macro_helper.h>
#include <embb/base/c/internal/atomic/atomic_variables.h>
#include <string.h>
/*
* See file and_assign.h for a detailed (and operation independent) description
* of the following macro.
*/
#define EMBB_ATOMIC_INTERNAL_DEFINE_INIT_METHOD(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) \
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_atomic_init_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)(\
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable) { \
EMBB_ATOMIC_MUTEX_INIT(variable->internal_mutex); \
variable->marker = 0x12345678; \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
#define EMBB_ATOMIC_METHOD_TO_GENERATE INIT_METHOD
#include <embb/base/c/internal/atomic/generate_atomic_implementation_template.h>
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
#endif //DOXYGEN
#endif //EMBB_BASE_C_INTERNAL_ATOMIC_INIT_H_
base_c/include/embb/base/c/internal/atomic/load.h
View file @
3926d7a1
...
...
@@ -58,14 +58,12 @@
#define EMBB_DEFINE_LOAD(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) \
EMBB_CAT2(embb_internal__atomic_load_, EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value) { \
EMBB_ATOMIC_MUTEX_LOCK; \
/* no fence required for loads */
\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result; \
__asm__ __volatile__("mov" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "=q" (result) \
: "m" (*pointer_to_value) \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
return result; \
}
#else
...
...
@@ -121,10 +119,13 @@ EMBB_DEFINE_LOAD(4, "")
*/
#define EMBB_ATOMIC_INTERNAL_DEFINE_LOAD_METHOD(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) \
EMBB_PLATFORM_INLINE EMBB_ATOMIC_PARAMETER_TYPE_NATIVE EMBB_CAT2(embb_atomic_load_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)(\
const EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable) { \
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable) { \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) \
return_val = (EMBB_CAT2(embb_internal__atomic_load_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)(\
(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)(&(variable->internal_variable)))); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
EMBB_ATOMIC_PARAMETER_TYPE_NATIVE return_val_pun; \
memcpy(&return_val_pun, &return_val, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
return return_val_pun; \
...
...
base_c/include/embb/base/c/internal/atomic/or_assign.h
View file @
3926d7a1
...
...
@@ -56,12 +56,10 @@
#define EMBB_DEFINE_OR_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_or_assign_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
EMBB_ATOMIC_MUTEX_LOCK; \
__asm__ __volatile__("lock or" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (value) \
: \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
}
#else
...
...
@@ -125,8 +123,11 @@ EMBB_DEFINE_OR_ASSIGN(4, "")
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_atomic_or_assign_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)(EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun;\
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE));\
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(embb_internal__atomic_or_assign_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)\
(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
...
...
base_c/include/embb/base/c/internal/atomic/store.h
View file @
3926d7a1
...
...
@@ -57,13 +57,11 @@
#define EMBB_DEFINE_STORE(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX)\
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_store_, EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value) {\
EMBB_ATOMIC_MUTEX_LOCK; \
/*the lock prefix is implicit for xchg*/
\
__asm__ __volatile__("xchg" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (new_value) \
: \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
}
#else
#error "No atomic fetch and store implementation found"
...
...
@@ -120,8 +118,11 @@ EMBB_DEFINE_STORE(4, "")
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_atomic_store_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)(EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun; \
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(embb_internal__atomic_store_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)\
(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
...
...
base_c/include/embb/base/c/internal/atomic/swap.h
View file @
3926d7a1
...
...
@@ -58,13 +58,11 @@
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) EMBB_CAT2(embb_internal__atomic_swap_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value)\
{ \
EMBB_ATOMIC_MUTEX_LOCK; \
/*the lock prefix is implicit for xchg*/
\
__asm__ __volatile__("xchg" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (new_value) \
: \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
return new_value; \
}
#else
...
...
@@ -129,8 +127,11 @@ EMBB_DEFINE_SWAP(4, "")
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun; \
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) \
return_val = EMBB_CAT2(embb_internal__atomic_swap_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
EMBB_ATOMIC_PARAMETER_TYPE_NATIVE return_val_pun; \
memcpy(&return_val_pun, &return_val, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE)); \
return return_val_pun; \
...
...
base_c/include/embb/base/c/internal/atomic/xor_assign.h
View file @
3926d7a1
...
...
@@ -57,12 +57,10 @@
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_xor_assign_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
EMBB_ATOMIC_MUTEX_LOCK; \
__asm__ __volatile__("lock xor" EMBB_ATOMIC_X86_SIZE_SUFFIX " %1, %0" \
: "+m" (*pointer_to_value), "+q" (value) \
: \
: "memory"); \
EMBB_ATOMIC_MUTEX_UNLOCK; \
}
#else
...
...
@@ -127,8 +125,11 @@ EMBB_DEFINE_XOR_ASSIGN(4, "")
EMBB_CAT2(embb_atomic_, EMBB_ATOMIC_PARAMETER_ATOMIC_TYPE_SUFFIX)* variable, EMBB_ATOMIC_PARAMETER_TYPE_NATIVE value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) value_pun;\
memcpy(&value_pun, &value, sizeof(EMBB_ATOMIC_PARAMETER_TYPE_NATIVE));\
EMBB_ATOMIC_INIT_CHECK(variable); \
EMBB_ATOMIC_MUTEX_LOCK(variable->internal_mutex); \
EMBB_CAT2(embb_internal__atomic_xor_assign_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE)((EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_ATOMIC_PARAMETER_TYPE_SIZE) volatile *)\
(&(variable->internal_variable)), value_pun); \
EMBB_ATOMIC_MUTEX_UNLOCK(variable->internal_mutex); \
}
#undef EMBB_ATOMIC_METHOD_TO_GENERATE
...
...
base_c/src/atomic.c
View file @
3926d7a1
...
...
@@ -46,17 +46,3 @@ void __embb_atomic_internal_compile_time_checks() {
BUILD_BUG_ON
(
sizeof
(
ptrdiff_t
)
!=
EMBB_PTRDIFF_T_TYPE_SIZE
);
BUILD_BUG_ON
(
sizeof
(
uintmax_t
)
!=
EMBB_UINTMAX_T_TYPE_SIZE
);
}
#ifdef EMBB_THREADING_ANALYSIS_MODE
embb_mutex_t
embb_atomic_mutex
;
void
embb_atomic_initialize
()
{
embb_mutex_init
(
&
embb_atomic_mutex
,
EMBB_MUTEX_PLAIN
);
}
void
embb_atomic_finalize
()
{
embb_mutex_destroy
(
&
embb_atomic_mutex
);
}
#endif
base_c/src/counter.c
View file @
3926d7a1
...
...
@@ -33,6 +33,7 @@ int embb_counter_init(embb_counter_t* counter) {
if
(
counter
==
NULL
)
{
return
EMBB_ERROR
;
}
embb_atomic_init_unsigned_int
(
&
(
counter
->
value
));
embb_atomic_store_unsigned_int
(
&
(
counter
->
value
),
0
);
return
EMBB_SUCCESS
;
}
...
...
@@ -55,7 +56,7 @@ unsigned int embb_counter_decrement(embb_counter_t* counter) {
void
embb_counter_destroy
(
embb_counter_t
*
counter
)
{
assert
(
counter
!=
NULL
);
EMBB_UNUSED_IN_RELEASE
(
counter
);
embb_atomic_destroy_unsigned_int
(
&
(
counter
->
value
)
);
}
base_c/src/internal/thread_index.c
View file @
3926d7a1
...
...
@@ -40,18 +40,18 @@
* This function has local scope.
*/
static
int
embb_max_number_thread_indices_max
=
0
;
static
embb_atomic_int
embb_max_number_thread_indices_flag
=
{
0
}
;
static
EMBB_BASE_BASIC_TYPE_SIZE_4
embb_max_number_thread_indices_flag
=
0
;
unsigned
int
*
embb_max_number_thread_indices
()
{
int
compare_to
=
0
;
if
(
embb_
atomic_load_int
(
&
embb_max_number_thread_indices_flag
)
!=
2
)
{
if
(
embb_
atomic_compare_and_swap_int
(
EMBB_BASE_BASIC_TYPE_SIZE_4
compare_to
=
0
;
if
(
embb_
internal__atomic_load_4
(
&
embb_max_number_thread_indices_flag
)
!=
2
)
{
if
(
embb_
internal__atomic_compare_and_swap_4
(
&
embb_max_number_thread_indices_flag
,
&
compare_to
,
1
))
{
embb_max_number_thread_indices_max
=
(
int
)(
embb_core_count_available
()
*
2
);
embb_
atomic_store_int
(
&
embb_max_number_thread_indices_flag
,
2
);
embb_
internal__atomic_store_4
(
&
embb_max_number_thread_indices_flag
,
2
);
}
while
(
embb_
atomic_load_int
(
&
embb_max_number_thread_indices_flag
)
!=
2
)
{}
while
(
embb_
internal__atomic_load_4
(
&
embb_max_number_thread_indices_flag
)
!=
2
)
{}
}
return
(
unsigned
int
*
)
&
embb_max_number_thread_indices_max
;
}
...
...
@@ -61,17 +61,17 @@ unsigned int* embb_max_number_thread_indices() {
*
* This function has local scope.
*/
static
embb_atomic_int
embb_thread_index_counter_flag
=
{
0
}
;
static
EMBB_BASE_BASIC_TYPE_SIZE_4
embb_thread_index_counter_flag
=
0
;
static
embb_counter_t
embb_thread_index_counter_index
;
embb_counter_t
*
embb_thread_index_counter
()
{
int
compare_to
=
0
;
if
(
embb_
atomic_load_int
(
&
embb_thread_index_counter_flag
)
!=
2
)
{
if
(
embb_
atomic_compare_and_swap_int
(
EMBB_BASE_BASIC_TYPE_SIZE_4
compare_to
=
0
;
if
(
embb_
internal__atomic_load_4
(
&
embb_thread_index_counter_flag
)
!=
2
)
{
if
(
embb_
internal__atomic_compare_and_swap_4
(
&
embb_thread_index_counter_flag
,
&
compare_to
,
1
))
{
embb_counter_init
(
&
embb_thread_index_counter_index
);
embb_
atomic_store_int
(
&
embb_thread_index_counter_flag
,
2
);
embb_
internal__atomic_store_4
(
&
embb_thread_index_counter_flag
,
2
);
}
while
(
embb_
atomic_load_int
(
&
embb_thread_index_counter_flag
)
!=
2
)
{}
while
(
embb_
internal__atomic_load_4
(
&
embb_thread_index_counter_flag
)
!=
2
)
{}
}
return
&
embb_thread_index_counter_index
;
}
...
...
base_c/src/memory_allocation.c
View file @
3926d7a1
...
...
@@ -33,7 +33,7 @@
#ifdef EMBB_DEBUG
static
embb_atomic_long
embb_bytes_allocated
=
{
0
}
;
static
EMBB_BASE_BASIC_TYPE_SIZE_4
embb_bytes_allocated
=
0
;
enum
{
// Make the marking unlikely to be something else
...
...
@@ -49,7 +49,7 @@ void* embb_alloc(size_t bytes) {
if
(
allocated
==
NULL
)
return
NULL
;
embb_
atomic_fetch_and_add_long
(
embb_
internal__atomic_fetch_and_add_4
(
&
embb_bytes_allocated
,
(
long
)
bytes_to_allocate
);
size_t
*
x_as_size_type
=
(
size_t
*
)
allocated
;
...
...
@@ -72,7 +72,7 @@ void embb_free(void * ptr) {
(
*
alloc_type
)
=
(
size_t
)
INVALID_ALLOCATION
;
embb_
atomic_fetch_and_add_long
(
embb_
internal__atomic_fetch_and_add_4
(
&
embb_bytes_allocated
,
(
long
)(
0
-
(
size_t
)(
*
bytes_allocated
)));
free
((
size_t
*
)
ptr
-
2
);
...
...
@@ -127,7 +127,7 @@ void* embb_alloc_aligned(size_t alignment, size_t size) {
x_as_size_type
[
-
2
]
=
(
size_t
)
allocated
;
x_as_size_type
[
-
3
]
=
bytes_to_allocate
;
embb_
atomic_fetch_and_add_long
(
embb_
internal__atomic_fetch_and_add_4
(
&
embb_bytes_allocated
,
(
long
)
bytes_to_allocate
);
return
x
;
...
...
@@ -144,14 +144,14 @@ void embb_free_aligned(void* ptr) {
ptr_conv
[
-
1
]
=
(
size_t
)
INVALID_ALLOCATION
;
embb_
atomic_fetch_and_add_long
(
embb_
internal__atomic_fetch_and_add_4
(
&
embb_bytes_allocated
,
(
long
)((
long
)
0
-
ptr_conv
[
-
3
]));
free
((
void
*
)
ptr_conv
[
-
2
]);
}
size_t
embb_get_bytes_allocated
()
{
return
(
size_t
)(
embb_
atomic_load_long
(
&
embb_bytes_allocated
));
return
(
size_t
)(
embb_
internal__atomic_load_4
(
&
embb_bytes_allocated
));
}
#else // EMBB_DEBUG
...
...
base_c/src/mutex.c
View file @
3926d7a1
...
...
@@ -149,6 +149,7 @@ int embb_spin_init(embb_spinlock_t* spinlock) {
}
// For now, store the initial value. In the future will use atomic init
// function (as soon as available).
embb_atomic_init_int
(
&
spinlock
->
atomic_spin_variable_
);
embb_atomic_store_int
(
&
spinlock
->
atomic_spin_variable_
,
0
);
return
EMBB_SUCCESS
;
}
...
...
@@ -207,7 +208,5 @@ int embb_spin_unlock(embb_spinlock_t* spinlock) {
void
embb_spin_destroy
(
embb_spinlock_t
*
spinlock
)
{
assert
(
NULL
!=
spinlock
);
// for now, doing nothing here... in future, will call the respective
// destroy function for atomics...
EMBB_UNUSED
(
spinlock
);
embb_atomic_destroy_int
(
&
spinlock
->
atomic_spin_variable_
);
}
base_c/test/main.cc
View file @
3926d7a1
...
...
@@ -55,8 +55,6 @@ using embb::base::test::ThreadTest;
using
embb
::
base
::
test
::
ThreadSpecificStorageTest
;
PT_MAIN
(
"Base C"
)
{
embb_atomic_initialize
();
embb_log_set_log_level
(
EMBB_LOG_LEVEL_WARNING
);
unsigned
int
max_threads
=
static_cast
<
unsigned
int
>
(
2
*
partest
::
TestSuite
::
GetDefaultNumThreads
());
...
...
@@ -74,6 +72,4 @@ PT_MAIN("Base C") {
PT_RUN
(
ThreadTest
);
PT_RUN
(
ThreadSpecificStorageTest
);
PT_EXPECT
(
embb_get_bytes_allocated
()
==
0
);
embb_atomic_finalize
();
}
base_c/test/thread_index_test.cc
View file @
3926d7a1
...
...
@@ -36,13 +36,22 @@ namespace embb {
namespace
base
{
namespace
test
{
embb_atomic_int
flag
;
ThreadIndexTest
::
ThreadIndexTest
()
:
number_threads_
(
partest
::
TestSuite
::
GetDefaultNumThreads
())
{
embb_atomic_init_int
(
&
flag
);
embb_atomic_store_int
(
&
flag
,
1
);
CreateUnit
(
"Test 0 indices"
).
Add
(
&
ThreadIndexTest
::
Test0
,
this
);
CreateUnit
(
"Test 1 index"
).
Add
(
&
ThreadIndexTest
::
Test1
,
this
);
CreateUnit
(
"Test N indices"
).
Add
(
&
ThreadIndexTest
::
TestN
,
this
,
1
);
}
ThreadIndexTest
::~
ThreadIndexTest
()
{
embb_atomic_destroy_int
(
&
flag
);
}
void
ThreadIndexTest
::
Test0
()
{
embb_internal_thread_index_reset
();
unsigned
int
old_max
=
embb_thread_get_max_count
();
...
...
@@ -78,8 +87,6 @@ void ThreadIndexTest::Test1() {
embb_internal_thread_index_set_max
(
old_max
);
}
embb_atomic_int
flag
=
{
1
};
void
ThreadIndexTest
::
TestN
()
{
embb_internal_thread_index_reset
();
unsigned
int
old_max
=
embb_thread_get_max_count
();
...
...
@@ -106,6 +113,8 @@ void ThreadIndexTest::TestN() {
embb_thread_join
(
&
thread
,
NULL
);
delete
[]
threads
;
embb_internal_thread_index_set_max
(
old_max
);
embb_atomic_destroy_int
(
&
flag
);
}
int
ThreadStart
(
void
*
arg
)
{
...
...
base_c/test/thread_index_test.h
View file @
3926d7a1
...
...
@@ -36,10 +36,15 @@ namespace test {
class
ThreadIndexTest
:
public
partest
::
TestCase
{
public
:
/**
* Adds test methods.
* Adds test methods
and allocates temporary data
.
*/
ThreadIndexTest
();
/**
* Destroys temporary data.
*/
~
ThreadIndexTest
();
private
:
/**
* Tests 0 available indices.
...
...
base_cpp/include/embb/base/internal/atomic/atomic_arithmetic.h
View file @
3926d7a1
...
...
@@ -117,8 +117,10 @@ FetchAndAdd(DifferenceType val) {
NativeType
native_desired
;
memcpy
(
&
native_desired
,
&
desired
,
sizeof
(
desired
));
EMBB_ATOMIC_MUTEX_LOCK
(
internal_mutex
);
NativeType
storage_value
=
fetch_and_add_implementation
<
NativeType
>::
fetch_and_add
(
&
this
->
AtomicValue
,
native_desired
);
EMBB_ATOMIC_MUTEX_UNLOCK
(
internal_mutex
);
memcpy
(
&
return_value
,
&
storage_value
,
sizeof
(
return_value
));
return
return_value
;
...
...
base_cpp/include/embb/base/internal/atomic/atomic_base.h
View file @
3926d7a1
...
...
@@ -58,6 +58,10 @@ class AtomicBase {
mutable
NativeType
AtomicValue
;
#ifdef EMBB_THREADING_ANALYSIS_MODE
embb_mutex_t
internal_mutex
;
#endif
public
:
/**
* Default constructor.
...
...
@@ -73,36 +77,48 @@ class AtomicBase {
*/
explicit
AtomicBase
(
BaseType
val
);
/**
* Destructor.
*/
~
AtomicBase
();
// The members below are documented in atomic.h
BaseType
operator
=
(
BaseType
val
);
operator
BaseType
()
const
;
operator
BaseType
();
bool
IsLockFree
()
const
;
bool
IsArithmetic
()
const
;
bool
IsInteger
()
const
;
bool
IsPointer
()
const
;
void
Store
(
BaseType
val
);
BaseType
Load
()
const
;
BaseType
Load
();
BaseType
Swap
(
BaseType
val
);
bool
CompareAndSwap
(
BaseType
&
expected
,
BaseType
desired
);
};
template
<
typename
BaseType
>
inline
AtomicBase
<
BaseType
>::
AtomicBase
()
:
AtomicValue
(
0
)
{
EMBB_ATOMIC_MUTEX_INIT
(
internal_mutex
);
}
template
<
typename
BaseType
>
inline
AtomicBase
<
BaseType
>::
AtomicBase
(
BaseType
val
)
/*: AtomicValue(val)*/
{
EMBB_ATOMIC_MUTEX_INIT
(
internal_mutex
);
memcpy
(
&
AtomicValue
,
&
val
,
sizeof
(
AtomicValue
));
}
template
<
typename
BaseType
>
inline
AtomicBase
<
BaseType
>::~
AtomicBase
()
{
EMBB_ATOMIC_MUTEX_DESTROY
(
internal_mutex
);
}
template
<
typename
BaseType
>
inline
BaseType
AtomicBase
<
BaseType
>::
operator
=
(
BaseType
val
)
{
Store
(
val
);
return
val
;
}
template
<
typename
BaseType
>
inline
AtomicBase
<
BaseType
>::
operator
BaseType
()
const
{
inline
AtomicBase
<
BaseType
>::
operator
BaseType
()
{
return
Load
();
}
...
...
@@ -132,16 +148,20 @@ inline void AtomicBase<BaseType>::Store(BaseType val) {
// anyway...
memcpy
(
&
storage_value
,
&
val
,
sizeof
(
storage_value
));
EMBB_ATOMIC_MUTEX_LOCK
(
internal_mutex
);
store_implementation
<
NativeType
>
::
Store
(
&
AtomicValue
,
storage_value
);
EMBB_ATOMIC_MUTEX_UNLOCK
(
internal_mutex
);
}
template
<
typename
BaseType
>
inline
BaseType
AtomicBase
<
BaseType
>::
Load
()
const
{
inline
BaseType
AtomicBase
<
BaseType
>::
Load
()
{
BaseType
return_value
;
EMBB_ATOMIC_MUTEX_LOCK
(
internal_mutex
);
NativeType
storage_value
=
load_implementation
<
NativeType
>::
Load
(
&
AtomicValue
);