2008-08-06 11:15:24 -07:00
|
|
|
/* EINA - EFL data type library
|
|
|
|
* Copyright (C) 2008 Cedric Bail
|
|
|
|
*
|
|
|
|
* This library is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU Lesser General Public
|
|
|
|
* License as published by the Free Software Foundation; either
|
|
|
|
* version 2.1 of the License, or (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This library is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
* Lesser General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU Lesser General Public
|
|
|
|
* License along with this library;
|
|
|
|
* if not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*/
|
|
|
|
|
2008-08-28 00:46:42 -07:00
|
|
|
#ifdef HAVE_CONFIG_H
|
|
|
|
# include "config.h"
|
|
|
|
#endif
|
|
|
|
|
2010-08-16 23:58:26 -07:00
|
|
|
#include <stdio.h>
|
2013-02-11 17:42:47 -08:00
|
|
|
#include <time.h>
|
2010-08-16 23:58:26 -07:00
|
|
|
|
2011-08-09 01:47:57 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2011-09-18 03:13:29 -07:00
|
|
|
# ifdef HAVE_SYS_TYPES_H
|
2011-08-09 01:47:57 -07:00
|
|
|
# include <sys/types.h>
|
2011-09-18 03:13:29 -07:00
|
|
|
# endif
|
2013-01-10 12:25:26 -08:00
|
|
|
# include <unistd.h>
|
2011-08-09 01:47:57 -07:00
|
|
|
#endif
|
|
|
|
|
2012-03-25 04:12:32 -07:00
|
|
|
#ifdef HAVE_MCHECK_H
|
2011-09-20 04:28:25 -07:00
|
|
|
# ifdef HAVE_MTRACE
|
|
|
|
# define MT 1
|
|
|
|
# endif
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#ifdef MT
|
|
|
|
#include <mcheck.h>
|
|
|
|
#endif
|
|
|
|
|
2011-05-02 04:20:00 -07:00
|
|
|
#include "eina_lock.h"
|
2009-08-28 05:03:34 -07:00
|
|
|
#include "eina_config.h"
|
2009-09-03 18:48:36 -07:00
|
|
|
#include "eina_private.h"
|
2009-01-23 08:11:45 -08:00
|
|
|
#include "eina_types.h"
|
|
|
|
#include "eina_main.h"
|
|
|
|
#include "eina_error.h"
|
2009-08-25 14:26:27 -07:00
|
|
|
#include "eina_log.h"
|
2009-01-23 08:11:45 -08:00
|
|
|
#include "eina_hash.h"
|
2010-07-27 20:33:49 -07:00
|
|
|
#include "eina_binshare.h"
|
2009-01-23 08:11:45 -08:00
|
|
|
#include "eina_stringshare.h"
|
2010-07-27 01:55:23 -07:00
|
|
|
#include "eina_ustringshare.h"
|
2009-01-23 08:11:45 -08:00
|
|
|
#include "eina_list.h"
|
2009-09-04 06:43:44 -07:00
|
|
|
#include "eina_matrixsparse.h"
|
2009-01-23 08:11:45 -08:00
|
|
|
#include "eina_array.h"
|
|
|
|
#include "eina_benchmark.h"
|
|
|
|
#include "eina_magic.h"
|
2009-04-09 08:51:32 -07:00
|
|
|
#include "eina_rectangle.h"
|
2009-09-03 18:48:36 -07:00
|
|
|
#include "eina_safety_checks.h"
|
2011-10-03 19:33:00 -07:00
|
|
|
#include "eina_inlist.h"
|
2012-01-09 15:24:18 -08:00
|
|
|
#include "eina_inarray.h"
|
add eina_value.
eina value is a generic value storage, it's quite efficient to space
(16 bytes) and speed (inlines for basic types).
It's basically a structure describing how to manage memory
(Eina_Value_Type), with default implementation for char, short, int,
long, int64_t (and unsigned variants), float, double, stringshare and
string.
If a type 'value_size' is smaller than 8 bytes, it's stored
inline. Otherwise a value is allocated and managed.
Most of the methods are inline, with special handling for char, short,
int... Then no extra calls are made, allowing the compiler to optimize
them.
For array of a single type it is recommend to use Eina_Value_Array, as
it will efficiently store and access members (just a char if subtype
is EINA_VALUE_TYPE_CHAR, etc).
It can copy itself, compare itself. Including arrays.
It would be nice to have something that converts between EET and this.
SVN revision: 67035
2012-01-10 18:20:26 -08:00
|
|
|
#include "eina_value.h"
|
2015-05-10 03:05:54 -07:00
|
|
|
#include "eina_evlog.h"
|
2016-11-04 03:06:15 -07:00
|
|
|
#include "eina_freeq.h"
|
2017-01-10 22:34:15 -08:00
|
|
|
#include "eina_slstr.h"
|
2018-02-18 13:12:58 -08:00
|
|
|
#include "eina_vpath.h"
|
2008-08-06 08:37:29 -07:00
|
|
|
|
2009-06-22 13:03:58 -07:00
|
|
|
/*============================================================================*
|
2010-07-27 19:37:05 -07:00
|
|
|
* Local *
|
|
|
|
*============================================================================*/
|
2009-06-22 13:03:58 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* @cond LOCAL
|
|
|
|
*/
|
|
|
|
|
2010-08-16 23:58:26 -07:00
|
|
|
static Eina_Version _version = { VMAJ, VMIN, VMIC, VREV };
|
|
|
|
|
2009-06-22 13:03:58 -07:00
|
|
|
static int _eina_main_count = 0;
|
2010-07-13 06:51:00 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2009-11-01 11:50:18 -08:00
|
|
|
static int _eina_main_thread_count = 0;
|
2009-12-09 00:34:09 -08:00
|
|
|
#endif
|
2009-09-03 18:48:36 -07:00
|
|
|
static int _eina_log_dom = -1;
|
2009-09-06 21:23:05 -07:00
|
|
|
|
|
|
|
#ifdef ERR
|
|
|
|
#undef ERR
|
|
|
|
#endif
|
2009-09-03 18:48:36 -07:00
|
|
|
#define ERR(...) EINA_LOG_DOM_ERR(_eina_log_dom, __VA_ARGS__)
|
2009-09-06 21:23:05 -07:00
|
|
|
|
|
|
|
#ifdef DBG
|
|
|
|
#undef DBG
|
|
|
|
#endif
|
2009-09-03 18:48:36 -07:00
|
|
|
#define DBG(...) EINA_LOG_DOM_DBG(_eina_log_dom, __VA_ARGS__)
|
2009-06-22 13:03:58 -07:00
|
|
|
|
2011-04-24 13:22:17 -07:00
|
|
|
EAPI Eina_Bool _eina_threads_activated = EINA_FALSE;
|
2011-08-09 01:48:57 -07:00
|
|
|
EAPI Eina_Error EINA_ERROR_NOT_MAIN_LOOP = 0;
|
2017-12-11 14:35:06 -08:00
|
|
|
EAPI Eina_Error EINA_ERROR_NOT_IMPLEMENTED = 0;
|
2013-02-03 23:52:56 -08:00
|
|
|
EAPI unsigned int eina_seed = 0;
|
2011-08-09 01:48:57 -07:00
|
|
|
|
2011-08-09 01:47:57 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
|
|
|
EAPI pthread_t _eina_main_loop;
|
2011-07-29 08:37:39 -07:00
|
|
|
#endif
|
|
|
|
|
2011-09-20 04:28:25 -07:00
|
|
|
#ifdef MT
|
|
|
|
static int _mt_enabled = 0;
|
|
|
|
#endif
|
|
|
|
|
2011-10-03 19:33:00 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2011-04-24 13:22:17 -07:00
|
|
|
EAPI int _eina_threads_debug = 0;
|
2011-10-06 22:56:43 -07:00
|
|
|
EAPI pthread_mutex_t _eina_tracking_lock;
|
2011-05-04 06:53:22 -07:00
|
|
|
EAPI Eina_Inlist *_eina_tracking = NULL;
|
2018-06-15 12:38:33 -07:00
|
|
|
extern Eina_Lock _sysmon_lock;
|
2011-04-24 13:22:17 -07:00
|
|
|
#endif
|
2010-10-12 09:53:30 -07:00
|
|
|
|
2009-09-06 15:21:56 -07:00
|
|
|
/* place module init/shutdown functions here to avoid other modules
|
|
|
|
* calling them by mistake.
|
|
|
|
*/
|
2010-07-27 19:37:05 -07:00
|
|
|
#define S(x) extern Eina_Bool eina_ ## x ## _init(void); \
|
|
|
|
extern Eina_Bool eina_ ## x ## _shutdown(void)
|
2015-05-04 19:35:16 -07:00
|
|
|
S(debug);
|
2015-05-10 03:05:54 -07:00
|
|
|
S(evlog);
|
2010-07-27 19:37:05 -07:00
|
|
|
S(log);
|
|
|
|
S(error);
|
|
|
|
S(safety_checks);
|
|
|
|
S(magic_string);
|
|
|
|
S(iterator);
|
|
|
|
S(accessor);
|
2012-01-09 15:24:18 -08:00
|
|
|
S(inarray);
|
2010-07-27 19:37:05 -07:00
|
|
|
S(array);
|
|
|
|
S(module);
|
|
|
|
S(mempool);
|
|
|
|
S(list);
|
2010-07-27 20:33:49 -07:00
|
|
|
S(binshare);
|
2010-07-27 19:37:05 -07:00
|
|
|
S(stringshare);
|
|
|
|
S(ustringshare);
|
|
|
|
S(matrixsparse);
|
|
|
|
S(convert);
|
|
|
|
S(benchmark);
|
|
|
|
S(rectangle);
|
|
|
|
S(strbuf);
|
|
|
|
S(ustrbuf);
|
|
|
|
S(quadtree);
|
2011-04-06 03:14:03 -07:00
|
|
|
S(simple_xml);
|
2011-09-02 22:31:25 -07:00
|
|
|
S(prefix);
|
add eina_value.
eina value is a generic value storage, it's quite efficient to space
(16 bytes) and speed (inlines for basic types).
It's basically a structure describing how to manage memory
(Eina_Value_Type), with default implementation for char, short, int,
long, int64_t (and unsigned variants), float, double, stringshare and
string.
If a type 'value_size' is smaller than 8 bytes, it's stored
inline. Otherwise a value is allocated and managed.
Most of the methods are inline, with special handling for char, short,
int... Then no extra calls are made, allowing the compiler to optimize
them.
For array of a single type it is recommend to use Eina_Value_Array, as
it will efficiently store and access members (just a char if subtype
is EINA_VALUE_TYPE_CHAR, etc).
It can copy itself, compare itself. Including arrays.
It would be nice to have something that converts between EET and this.
SVN revision: 67035
2012-01-10 18:20:26 -08:00
|
|
|
S(value);
|
2012-10-17 03:24:03 -07:00
|
|
|
S(tmpstr);
|
2012-10-18 22:47:33 -07:00
|
|
|
S(thread);
|
2013-01-08 01:17:56 -08:00
|
|
|
S(cow);
|
2013-10-02 02:31:10 -07:00
|
|
|
S(cpu);
|
2014-07-15 01:02:07 -07:00
|
|
|
S(thread_queue);
|
2016-04-22 10:58:25 -07:00
|
|
|
S(rbtree);
|
2016-10-24 12:13:39 -07:00
|
|
|
S(file);
|
2016-06-10 13:42:19 -07:00
|
|
|
S(safepointer);
|
2017-01-10 22:34:15 -08:00
|
|
|
S(slstr);
|
2017-08-08 14:10:36 -07:00
|
|
|
S(promise);
|
2018-02-18 13:12:58 -08:00
|
|
|
S(vpath);
|
2020-01-04 06:08:08 -08:00
|
|
|
S(abstract_content);
|
2009-09-06 15:21:56 -07:00
|
|
|
#undef S
|
|
|
|
|
|
|
|
struct eina_desc_setup
|
|
|
|
{
|
|
|
|
const char *name;
|
|
|
|
Eina_Bool (*init)(void);
|
|
|
|
Eina_Bool (*shutdown)(void);
|
|
|
|
};
|
|
|
|
|
|
|
|
static const struct eina_desc_setup _eina_desc_setup[] = {
|
2010-07-27 19:37:05 -07:00
|
|
|
#define S(x) {# x, eina_ ## x ## _init, eina_ ## x ## _shutdown}
|
|
|
|
/* log is a special case as it needs printf */
|
2018-06-15 13:40:23 -07:00
|
|
|
S(module),
|
|
|
|
S(mempool),
|
|
|
|
S(list),
|
2018-08-20 09:59:15 -07:00
|
|
|
S(stringshare),
|
|
|
|
S(vpath),
|
2015-05-04 19:35:16 -07:00
|
|
|
S(debug),
|
2015-05-10 03:05:54 -07:00
|
|
|
S(evlog),
|
2010-07-27 19:37:05 -07:00
|
|
|
S(error),
|
|
|
|
S(safety_checks),
|
|
|
|
S(magic_string),
|
|
|
|
S(iterator),
|
|
|
|
S(accessor),
|
2012-01-09 15:24:18 -08:00
|
|
|
S(inarray),
|
2010-07-27 19:37:05 -07:00
|
|
|
S(array),
|
2010-07-27 20:33:49 -07:00
|
|
|
S(binshare),
|
2010-07-27 19:37:05 -07:00
|
|
|
S(ustringshare),
|
|
|
|
S(matrixsparse),
|
|
|
|
S(convert),
|
|
|
|
S(benchmark),
|
|
|
|
S(rectangle),
|
|
|
|
S(strbuf),
|
|
|
|
S(ustrbuf),
|
2011-04-06 03:14:03 -07:00
|
|
|
S(quadtree),
|
2011-04-13 09:15:30 -07:00
|
|
|
S(simple_xml),
|
add eina_value.
eina value is a generic value storage, it's quite efficient to space
(16 bytes) and speed (inlines for basic types).
It's basically a structure describing how to manage memory
(Eina_Value_Type), with default implementation for char, short, int,
long, int64_t (and unsigned variants), float, double, stringshare and
string.
If a type 'value_size' is smaller than 8 bytes, it's stored
inline. Otherwise a value is allocated and managed.
Most of the methods are inline, with special handling for char, short,
int... Then no extra calls are made, allowing the compiler to optimize
them.
For array of a single type it is recommend to use Eina_Value_Array, as
it will efficiently store and access members (just a char if subtype
is EINA_VALUE_TYPE_CHAR, etc).
It can copy itself, compare itself. Including arrays.
It would be nice to have something that converts between EET and this.
SVN revision: 67035
2012-01-10 18:20:26 -08:00
|
|
|
S(prefix),
|
2012-01-20 17:30:09 -08:00
|
|
|
S(value),
|
2012-10-17 03:24:03 -07:00
|
|
|
S(tmpstr),
|
2013-01-08 01:17:56 -08:00
|
|
|
S(thread),
|
2013-10-02 02:31:10 -07:00
|
|
|
S(cow),
|
2014-07-15 01:02:07 -07:00
|
|
|
S(cpu),
|
2016-04-22 10:58:25 -07:00
|
|
|
S(thread_queue),
|
2016-05-06 12:32:10 -07:00
|
|
|
S(rbtree),
|
2016-10-24 12:13:39 -07:00
|
|
|
S(file),
|
2016-06-10 18:32:07 -07:00
|
|
|
S(safepointer),
|
2017-01-10 22:34:15 -08:00
|
|
|
S(slstr),
|
2017-08-08 14:10:36 -07:00
|
|
|
S(promise),
|
2020-01-04 06:08:08 -08:00
|
|
|
S(abstract_content)
|
2009-09-06 15:21:56 -07:00
|
|
|
#undef S
|
|
|
|
};
|
2010-07-27 19:37:05 -07:00
|
|
|
static const size_t _eina_desc_setup_len = sizeof(_eina_desc_setup) /
|
|
|
|
sizeof(_eina_desc_setup[0]);
|
2009-09-06 15:21:56 -07:00
|
|
|
|
|
|
|
static void
|
|
|
|
_eina_shutdown_from_desc(const struct eina_desc_setup *itr)
|
|
|
|
{
|
|
|
|
for (itr--; itr >= _eina_desc_setup; itr--)
|
|
|
|
{
|
2010-07-27 19:37:05 -07:00
|
|
|
if (!itr->shutdown())
|
|
|
|
ERR("Problems shutting down eina module '%s', ignored.", itr->name);
|
2009-09-06 15:21:56 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
eina_log_domain_unregister(_eina_log_dom);
|
|
|
|
_eina_log_dom = -1;
|
|
|
|
eina_log_shutdown();
|
|
|
|
}
|
|
|
|
|
2018-06-15 13:43:39 -07:00
|
|
|
static void
|
|
|
|
_eina_threads_do_shutdown(void)
|
|
|
|
{
|
|
|
|
#ifdef EINA_HAVE_DEBUG_THREADS
|
|
|
|
const Eina_Lock *lk;
|
|
|
|
|
|
|
|
pthread_mutex_lock(&_eina_tracking_lock);
|
|
|
|
if (_eina_tracking)
|
|
|
|
{
|
|
|
|
if (((Eina_Lock*)_eina_tracking != (&_sysmon_lock)) || (_eina_tracking->next))
|
|
|
|
{
|
|
|
|
fprintf(stderr, "*************************\n");
|
|
|
|
fprintf(stderr, "* The IMPOSSIBLE HAPPEN *\n");
|
|
|
|
fprintf(stderr, "* LOCK STILL TAKEN : *\n");
|
|
|
|
fprintf(stderr, "*************************\n");
|
|
|
|
EINA_INLIST_FOREACH(_eina_tracking, lk)
|
|
|
|
{
|
|
|
|
fprintf(stderr, "=======\n");
|
|
|
|
eina_lock_debug(lk);
|
|
|
|
}
|
|
|
|
fprintf(stderr, "*************************\n");
|
|
|
|
abort();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
pthread_mutex_unlock(&_eina_tracking_lock);
|
|
|
|
#endif
|
|
|
|
|
|
|
|
eina_share_common_threads_shutdown();
|
|
|
|
eina_log_threads_shutdown();
|
|
|
|
|
|
|
|
_eina_threads_activated = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2009-06-22 13:03:58 -07:00
|
|
|
/**
|
|
|
|
* @endcond
|
|
|
|
*/
|
|
|
|
|
2008-08-28 00:46:42 -07:00
|
|
|
/*============================================================================*
|
2010-07-27 19:37:05 -07:00
|
|
|
* Global *
|
|
|
|
*============================================================================*/
|
2008-08-28 00:46:42 -07:00
|
|
|
|
2010-08-16 23:58:26 -07:00
|
|
|
|
2008-08-28 00:46:42 -07:00
|
|
|
/*============================================================================*
|
2010-07-27 19:37:05 -07:00
|
|
|
* API *
|
|
|
|
*============================================================================*/
|
2008-08-28 00:46:42 -07:00
|
|
|
|
2010-08-16 23:58:26 -07:00
|
|
|
/**
|
|
|
|
* @var eina_version
|
|
|
|
* @brief Eina version (defined at configuration time)
|
|
|
|
*/
|
|
|
|
EAPI Eina_Version *eina_version = &_version;
|
|
|
|
|
2008-08-06 08:37:29 -07:00
|
|
|
EAPI int
|
|
|
|
eina_init(void)
|
|
|
|
{
|
2009-09-06 15:21:56 -07:00
|
|
|
const struct eina_desc_setup *itr, *itr_end;
|
|
|
|
|
|
|
|
if (EINA_LIKELY(_eina_main_count > 0))
|
2010-07-27 19:37:05 -07:00
|
|
|
return ++_eina_main_count;
|
2008-08-06 08:37:29 -07:00
|
|
|
|
2013-02-03 23:52:56 -08:00
|
|
|
srand(time(NULL));
|
|
|
|
while (eina_seed == 0)
|
|
|
|
eina_seed = rand();
|
|
|
|
|
2011-09-20 04:28:25 -07:00
|
|
|
#ifdef MT
|
|
|
|
if ((getenv("EINA_MTRACE")) && (getenv("MALLOC_TRACE")))
|
|
|
|
{
|
|
|
|
_mt_enabled = 1;
|
|
|
|
mtrace();
|
|
|
|
}
|
2011-12-20 03:00:59 -08:00
|
|
|
#endif
|
2017-02-28 02:46:56 -08:00
|
|
|
|
|
|
|
#ifdef EFL_HAVE_THREADS
|
|
|
|
_eina_main_loop = pthread_self();
|
|
|
|
#endif
|
|
|
|
|
2017-01-10 21:48:57 -08:00
|
|
|
eina_freeq_main_set(eina_freeq_new(EINA_FREEQ_DEFAULT));
|
2011-12-20 03:00:59 -08:00
|
|
|
|
2009-09-03 18:48:36 -07:00
|
|
|
if (!eina_log_init())
|
2009-06-05 21:22:21 -07:00
|
|
|
{
|
2010-07-27 19:37:05 -07:00
|
|
|
fprintf(stderr, "Could not initialize eina logging system.\n");
|
|
|
|
return 0;
|
2009-06-05 21:22:21 -07:00
|
|
|
}
|
2010-07-27 19:37:05 -07:00
|
|
|
|
2009-09-03 18:48:36 -07:00
|
|
|
_eina_log_dom = eina_log_domain_register("eina", EINA_LOG_COLOR_DEFAULT);
|
|
|
|
if (_eina_log_dom < 0)
|
2009-08-25 14:26:27 -07:00
|
|
|
{
|
2010-07-27 19:37:05 -07:00
|
|
|
EINA_LOG_ERR("Could not register log domain: eina");
|
|
|
|
eina_log_shutdown();
|
|
|
|
return 0;
|
2009-09-03 18:48:36 -07:00
|
|
|
}
|
|
|
|
|
2011-07-29 08:37:39 -07:00
|
|
|
#ifdef EINA_HAVE_DEBUG_THREADS
|
2011-10-06 22:56:43 -07:00
|
|
|
pthread_mutex_init(&_eina_tracking_lock, NULL);
|
2011-05-04 06:53:22 -07:00
|
|
|
|
|
|
|
if (getenv("EINA_DEBUG_THREADS"))
|
|
|
|
_eina_threads_debug = atoi(getenv("EINA_DEBUG_THREADS"));
|
|
|
|
#endif
|
|
|
|
|
2009-09-06 15:21:56 -07:00
|
|
|
itr = _eina_desc_setup;
|
|
|
|
itr_end = itr + _eina_desc_setup_len;
|
|
|
|
for (; itr < itr_end; itr++)
|
2009-09-03 17:53:19 -07:00
|
|
|
{
|
2010-07-27 19:37:05 -07:00
|
|
|
if (!itr->init())
|
|
|
|
{
|
|
|
|
ERR("Could not initialize eina module '%s'.", itr->name);
|
|
|
|
_eina_shutdown_from_desc(itr);
|
|
|
|
return 0;
|
|
|
|
}
|
2009-09-03 17:53:19 -07:00
|
|
|
}
|
|
|
|
|
2012-04-19 02:25:54 -07:00
|
|
|
eina_cpu_count_internal();
|
|
|
|
|
2017-11-17 11:11:48 -08:00
|
|
|
EINA_ERROR_NOT_MAIN_LOOP = eina_error_msg_static_register("Not in main loop.");
|
2018-01-02 04:54:52 -08:00
|
|
|
EINA_ERROR_NOT_IMPLEMENTED = eina_error_msg_static_register("Functionality not implemented.");
|
2017-11-17 11:11:48 -08:00
|
|
|
|
2013-03-27 05:39:55 -07:00
|
|
|
eina_log_timing(_eina_log_dom, EINA_LOG_STATE_STOP, EINA_LOG_STATE_INIT);
|
|
|
|
|
2009-09-06 15:21:56 -07:00
|
|
|
_eina_main_count = 1;
|
2015-05-10 03:05:54 -07:00
|
|
|
eina_evlog("-eina_init", NULL, 0.0, NULL);
|
2009-09-06 15:21:56 -07:00
|
|
|
return 1;
|
2008-08-06 08:37:29 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
EAPI int
|
|
|
|
eina_shutdown(void)
|
|
|
|
{
|
2012-05-30 03:08:41 -07:00
|
|
|
if (_eina_main_count <= 0)
|
|
|
|
{
|
|
|
|
ERR("Init count not greater than 0 in shutdown.");
|
|
|
|
return 0;
|
|
|
|
}
|
2009-09-06 15:21:56 -07:00
|
|
|
_eina_main_count--;
|
|
|
|
if (EINA_UNLIKELY(_eina_main_count == 0))
|
2011-04-24 08:54:09 -07:00
|
|
|
{
|
2013-03-27 05:39:55 -07:00
|
|
|
eina_log_timing(_eina_log_dom,
|
|
|
|
EINA_LOG_STATE_START,
|
|
|
|
EINA_LOG_STATE_SHUTDOWN);
|
|
|
|
|
2011-04-24 08:54:09 -07:00
|
|
|
_eina_shutdown_from_desc(_eina_desc_setup + _eina_desc_setup_len);
|
|
|
|
|
2018-06-15 13:43:39 -07:00
|
|
|
if (_eina_threads_activated && (!_eina_main_thread_count))
|
|
|
|
_eina_threads_do_shutdown();
|
2011-05-04 06:53:22 -07:00
|
|
|
#ifdef EINA_HAVE_DEBUG_THREADS
|
2011-10-06 22:56:43 -07:00
|
|
|
pthread_mutex_destroy(&_eina_tracking_lock);
|
2011-05-04 06:53:22 -07:00
|
|
|
#endif
|
2016-11-04 03:06:15 -07:00
|
|
|
eina_freeq_free(eina_freeq_main_get());
|
2011-09-20 04:28:25 -07:00
|
|
|
#ifdef MT
|
|
|
|
if (_mt_enabled)
|
|
|
|
{
|
|
|
|
muntrace();
|
|
|
|
_mt_enabled = 0;
|
|
|
|
}
|
2011-12-20 03:00:59 -08:00
|
|
|
#endif
|
2011-04-24 08:54:09 -07:00
|
|
|
}
|
2010-07-27 19:37:05 -07:00
|
|
|
|
2009-09-06 15:21:56 -07:00
|
|
|
return _eina_main_count;
|
2008-08-06 08:37:29 -07:00
|
|
|
}
|
|
|
|
|
2009-11-01 11:50:18 -08:00
|
|
|
|
|
|
|
EAPI int
|
|
|
|
eina_threads_init(void)
|
|
|
|
{
|
2010-07-13 06:51:00 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2010-07-27 19:37:05 -07:00
|
|
|
int ret;
|
2010-07-13 06:51:00 -07:00
|
|
|
|
2011-05-02 04:20:00 -07:00
|
|
|
#ifdef EINA_HAVE_DEBUG_THREADS
|
|
|
|
assert(pthread_equal(_eina_main_loop, pthread_self()));
|
|
|
|
#endif
|
2010-07-27 19:37:05 -07:00
|
|
|
|
|
|
|
++_eina_main_thread_count;
|
|
|
|
ret = _eina_main_thread_count;
|
|
|
|
|
|
|
|
if(_eina_main_thread_count > 1)
|
2011-05-06 02:07:26 -07:00
|
|
|
return ret;
|
2009-11-01 11:50:18 -08:00
|
|
|
|
2010-07-27 19:37:05 -07:00
|
|
|
eina_share_common_threads_init();
|
|
|
|
eina_log_threads_init();
|
2011-04-24 13:22:17 -07:00
|
|
|
_eina_threads_activated = EINA_TRUE;
|
2009-11-01 11:50:18 -08:00
|
|
|
|
2010-07-27 19:37:05 -07:00
|
|
|
return ret;
|
2009-11-01 11:50:18 -08:00
|
|
|
#else
|
2010-07-27 19:37:05 -07:00
|
|
|
return 0;
|
2009-11-01 11:50:18 -08:00
|
|
|
#endif
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI int
|
|
|
|
eina_threads_shutdown(void)
|
|
|
|
{
|
2010-07-13 06:51:00 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2010-07-27 19:37:05 -07:00
|
|
|
int ret;
|
2009-11-01 11:50:18 -08:00
|
|
|
|
2011-05-02 04:20:00 -07:00
|
|
|
#ifdef EINA_HAVE_DEBUG_THREADS
|
|
|
|
assert(pthread_equal(_eina_main_loop, pthread_self()));
|
|
|
|
assert(_eina_main_thread_count > 0);
|
2011-05-09 03:29:55 -07:00
|
|
|
#endif
|
|
|
|
|
|
|
|
ret = --_eina_main_thread_count;
|
|
|
|
if(_eina_main_thread_count > 0)
|
|
|
|
return ret;
|
2011-05-04 06:53:22 -07:00
|
|
|
|
2018-06-15 13:43:39 -07:00
|
|
|
if (!_eina_main_count)
|
|
|
|
_eina_threads_do_shutdown();
|
2010-07-13 06:51:00 -07:00
|
|
|
|
2010-07-27 19:37:05 -07:00
|
|
|
return ret;
|
2009-11-01 11:50:18 -08:00
|
|
|
#else
|
2010-07-27 19:37:05 -07:00
|
|
|
return 0;
|
2009-11-01 11:50:18 -08:00
|
|
|
#endif
|
|
|
|
}
|
|
|
|
|
2011-07-29 07:56:42 -07:00
|
|
|
EAPI Eina_Bool
|
|
|
|
eina_main_loop_is(void)
|
|
|
|
{
|
2011-08-09 01:47:57 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2015-11-06 01:34:50 -08:00
|
|
|
# ifdef __GNUC__
|
|
|
|
/* pthread_self() can't be optimized, it's a single asm "movl" */
|
|
|
|
if (__builtin_types_compatible_p(pthread_t, unsigned long int))
|
|
|
|
return (pthread_self() == _eina_main_loop);
|
|
|
|
else
|
|
|
|
# endif
|
|
|
|
if (pthread_equal(_eina_main_loop, pthread_self()))
|
2012-06-12 00:58:11 -07:00
|
|
|
return EINA_TRUE;
|
|
|
|
#endif
|
2011-07-29 08:37:39 -07:00
|
|
|
return EINA_FALSE;
|
2011-07-29 07:56:42 -07:00
|
|
|
}
|
|
|
|
|
2011-08-17 02:42:43 -07:00
|
|
|
/** The purpose of this API should not be documented, it is used only by the one who know what they are doing. */
|
|
|
|
EAPI void
|
|
|
|
eina_main_loop_define(void)
|
|
|
|
{
|
2011-08-26 09:13:29 -07:00
|
|
|
#ifdef EFL_HAVE_THREADS
|
2011-08-17 02:42:43 -07:00
|
|
|
_eina_main_loop = pthread_self();
|
2011-08-26 09:13:29 -07:00
|
|
|
#endif
|
2011-08-17 02:42:43 -07:00
|
|
|
}
|
|
|
|
|
2009-06-22 13:03:58 -07:00
|
|
|
/**
|
|
|
|
* @}
|
|
|
|
*/
|