8879ce0689747fdb3393bbb28cf0e5b7b1a0ff4f
[platform/core/uifw/dali-core.git] / dali / public-api / common / dali-common.h
1 #ifndef __DALI_COMMON_H__
2 #define __DALI_COMMON_H__
3
4 /*
5  * Copyright (c) 2015 Samsung Electronics Co., Ltd.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  */
20
21 // EXTERNAL INCLUDES
22
23 #ifdef EMSCRIPTEN
24 #include <emscripten/emscripten.h>
25 #endif
26
27 /*
28  * Definitions for shared library support
29  *
30  * If a library is configured with --enable-exportall or --enable-debug
31  * then HIDE_DALI_INTERNALS is not defined, and nothing is hidden.
32  * If it is configured without these options (the default), then HIDE_INTERNALS
33  * is defined when building the library, visibility is automatically hidden, and the explicit
34  * defines below come into use.
35  * When building a library that uses DALI, HIDE_DALI_INTERNALS
36  */
37 #if __GNUC__ >= 4
38 #  ifndef HIDE_DALI_INTERNALS
39 #    define DALI_EXPORT_API
40 #    define DALI_IMPORT_API
41 #    define DALI_INTERNAL
42 #  else
43 #    define DALI_EXPORT_API __attribute__ ((visibility ("default")))
44 #    define DALI_IMPORT_API __attribute__ ((visibility ("default")))
45 #    define DALI_INTERNAL   __attribute__ ((visibility ("hidden")))
46 #  endif
47 #else
48 /** Visibility attribute to show method definitions */
49 #  define DALI_EXPORT_API
50 /** Visibility attribute to show declarations */
51 #  define DALI_IMPORT_API
52 /** Visibility attribute to hide declarations */
53 #  define DALI_INTERNAL
54 #endif
55
56 #if defined (__GXX_EXPERIMENTAL_CXX0X__) || (__cplusplus >= 201103L)
57 // C++0x support
58 #define _CPP11
59 #else
60 // C++0x not supported
61 #endif
62
63 #ifdef EMSCRIPTEN
64
65 #ifndef __clang__
66 # error not clang?
67 #endif
68
69 // clang cpp11 check is per feature
70 #if !__has_feature(cxx_constexpr)
71 # error constexpr needed for compile-time-math. Use -std=c+11
72 #endif
73
74 #define _CPP11
75
76 #endif
77
78 /**
79  * @brief Two macros to provide branch predictor information.
80  * DALI_LIKELY should be used when a branch is taken in almost all cases so the
81  * branch predictor can avoid pre-fetching the code for else branch
82  * DALI_UNLIKELY should be used when a branch is almost never taken
83  * @SINCE_1_0.0
84  */
85 #define DALI_LIKELY(expression)   __builtin_expect( !!(expression), 1 )
86 #define DALI_UNLIKELY(expression) __builtin_expect( !!(expression), 0 )
87
88 /**
89  * @brief The DALi namespace
90  * @SINCE_1_0.0
91  */
92 namespace Dali
93 {
94 /**
95  * @addtogroup dali_core_common
96  * @{
97  */
98
99 /**
100  * @brief Method to log assertion message in DALI_ASSERT_ALWAYS macro below.
101  *
102  * @SINCE_1_0.0
103  * @param[in] location Where the assertion occurred
104  * @param[in] condition The assertion condition
105  */
106 DALI_IMPORT_API void DaliAssertMessage( const char* location, const char* condition );
107
108 /**
109  * @brief Exception class for Dali Core library - Raised by assertions in codebase.
110  * @SINCE_1_0.0
111  */
112 class DALI_IMPORT_API DaliException
113 {
114 public:
115   /**
116    * @brief Constructor.
117    *
118    * Will always display a backtrace when raised in a debug build.
119    *
120    * @SINCE_1_0.0
121    * @param[in] location The location of the assertion
122    * @param[in] condition The assertion condition
123    */
124   DaliException( const char* location, const char* condition );
125
126   const char* location;
127   const char* condition;
128 };
129
130 /**
131  * @}
132  */
133 }// Dali
134
135 /**
136  * @brief An invariant concurrent assertion to ensure its argument always evaluates TRUE.
137  *
138  * Use this for rules that must always be true regardless of build options.
139  * For example, Actor must only ever have one parent.
140  * To be clear, this test remains compiled into release builds that are deployed
141  * on the platform.
142  * Semantically, a failure of this test is signalling that dali is giving up and
143  * quitting.
144  * Since we don't catch the exception, a failure on any thread other than event
145  * will propagate up the call stack and kill that thread.
146  * A failure on the event thread may give the application an opportunity to
147  * recover if there is an application-written exception handler on the call
148  * stack between the throw site and the thread root and the application is built
149  * with a compatible ABI.
150  * Handle this macro with care at the level you would if it expanded to:
151  *    if(!cond) { exit(EXIT_FAILURE); }
152  * (which it is often equivalent to in effect).
153  * It should not be used for simple parameter validation for instance.
154  */
155
156 /**
157  * @brief Strip assert location for release builds, assert text is descriptive enough
158  * This is to save space for low spec devices
159  * @SINCE_1_0.0
160  */
161 #if defined(DEBUG_ENABLED)
162 #define ASSERT_LOCATION __PRETTY_FUNCTION__
163 #else
164 #define ASSERT_LOCATION NULL
165 #endif
166
167 #ifdef EMSCRIPTEN
168
169 #define DALI_ASSERT_ALWAYS(cond)                \
170   if(DALI_UNLIKELY(!(cond))) \
171   { \
172     Dali::DaliAssertMessage( ASSERT_LOCATION, #cond );   \
173     throw Dali::DaliException( ASSERT_LOCATION, #cond );  \
174     EM_ASM(print(new Error().stack)); \
175   }
176 #else
177
178 #define DALI_ASSERT_ALWAYS(cond)                \
179   if(DALI_UNLIKELY(!(cond))) \
180   { \
181     Dali::DaliAssertMessage( ASSERT_LOCATION, #cond );   \
182     throw Dali::DaliException( ASSERT_LOCATION, #cond );  \
183   }
184 #endif
185
186 /**
187  * @brief An invariant concurrent assertion to ensure its argument evaluates TRUE in debug builds.
188  *
189  * Use this to sanity check algorithms and prevent internal programming errors
190  * @SINCE_1_0.0
191  */
192 #if defined(DEBUG_ENABLED)
193 #define DALI_ASSERT_DEBUG(cond) DALI_ASSERT_ALWAYS(cond)
194 #else
195 #define DALI_ASSERT_DEBUG(cond)
196 #endif
197
198 #endif // __DALI_COMMON_H__