we really should have data inside the loop object, so begin moving it
one small thing at a time. this is the basics that will allow multiple
efl loops. make an eo efl object and class for fd handlers that is efl loop
bound make fd handlers really bound to their parent loop and not global as
well as have a nice class/obj. create an message queue per loop and
put legacy ecore events on top of it... and a lot more.
this is not 100% done, but it's a lot of the core and groundwork.
various ecore_timer_add(), ecore_diler_add() etc. need changes.
The following still need doing:
ecore_timer (internal usage for sure)
ecore_idler (internal usage for sure)
ecore_idle_enterer
ecore_idle_exiter
ecore_pollers? (is the new efl loop stuff ok?)
ecore_exe (fork/spawn from any thread and track exe from that thread?)
ecore_signal code
ecore_throttle (should we have a single global too? we have per loop)
ecore_app ? (should every loop be given its own argv/argc?)
Lots of internal ecore code uses/calls these legacy calls and we
should have efl loop replacements and/or use the ones we have
The following will bedifferently designed for loop to loop
control/messaging/ipc:
ecore_thread
ecore_pipe
This reverts commit 2c6808e4ee.
this breaks a number of expectations and guarantees in efl:
* causes unexpected event iteration during app startup before main loop begins
- leads to event loss
* causes unexpected event iteration during app shutdown after main loop quits
- leads to invalid memory access
* causes recursive event iteration during event handler callbacks
- leads to ?????????????????????????????????????????????????????????????????
all of these can be easily seen by running enlightenment, and all of these cause
unexpected behaviors in enlightenment including, but not limited to, a lot of crashes
fix T5232
If a component emit Ecore_Event and they aren't processed before the
call it call ecore_shutdown, there is no way to prevent this event
from being triggered after the component at shutdown itself. Which
may well lead to a use after free case. As we don't know which event
are pending and we also are not shuting down ecore completely as they
are still other component using it, we can only flush all pending event
right away.
Sometimes during debug of efl_net we get some "extra" sockets from
DBus to talk to upower, localed, timedated... which are helpful in
real life, but pollutes debugging.
Since I don't want to contaminate examples with
ecore_app_no_system_modules(), which could lead users to naively copy
those and end without the system modules features, add an envvar that
I can define in my tests when I need them.
This moved all the eoid tables, eoid lookup caches, generation count
information ad eo_isa cache into a TLS segment of memory that is
thread private. There is also a shared domain for EO objects that all
threads can access, but it has an added cost of a lock. This means
objects accessed outside the thread they were created in cannot be
accessed by another thread unless they are adopted in temporarily, or
create4d with the shared domain active at the time of creation. child
objects will use their parent object domain if created with a parent
object passed in. If you were accessing EO (EFL) objects across threads
before then this will actually now cause your code to fail as it was
invalid before to do this as no actual objects were threadsafe in EFL,
so this will force things to "fail early".
ecore_thread_main_loop_begin() and end() still work as this uses the
eo domain adoption features to temporarily adopt a domain during this
section and then return it when done.
This returns speed back to eo brining the overhead in my tests of
lookup for the elm genlist autobounce test in elementary from about
5-7% down to 2.5-2.6%. A steep drop.
This does not mean everything is perfect. Still to do are:
1. Tests in the test suite
2. Some API's to help for sending objects from thread to thread
3. Make the eo call cache TLS data to make it also safe
4. Look at other locks in eo and probably move them to TLS data
5. Make eo resolve and call wrappers that call the real method func do
recursive mutex wrapping of the given object IF it is a shared object
to provide threadsafety transparently for shared objects (but adding
some overhead as a result)
6. Test test est, and that is why this commit is going in now for wider
testing
7. Decide how to make this work with sending IPC (between threads)
8. Deciding what makes an object sendable (a sendable property in base?)
9. Deciding what makes an object shareable (a sharable property in base?)
i've fixed almost all the eina init/shutdown pairs to do the right
thing now... except one (ecore_shutdown) with comment inline where
eo_shutdown is not called. if this is called we are in crash land.
this needs further inspection.
As we add more object in the main loop, they can't live in the top
namespace as they make little sense there (Efl.Fd !). For coherence,
everyone should in the loop namespace, so move timer there.
This reverts commit 546ff7bbba.
It seems that eo_del() is useful and removing it was creating bugs.
The issue is that the way we defined parents in eo, both the parent and
the programmer share a reference to the object. When we eo_unref() that
reference as the programmer, eo has no way to know it's this specific
reference we are freeing, and not a general one, so in some
circumstances, for example:
eo_ref(child);
eo_unref(child); // trying to delete here
eo_unref(container); // container is deleted here
eo_unref(child); // child already has 0 refs before this point.
We would have an issue with references and objects being freed too soon
and in general, issue with the references.
Having eo_del() solves that, because this one explicitly unparents if
there is a parent, meaning the reference ownership is explicitly taken
by the programmer.
eo_del() is essentially a convenience function around "check if has
parent, and if so unparent, otherwise, unref". Which should be used when
you want to delete an object although it has a parent, and is equivalent
to eo_unref() when it doesn't have one.
We used to have eo_del() as the mirrored action to eo_add(). No longer,
now you just always eo_unref() to delete an object. This change makes it
so the reference of the parent is shared with the reference the
programmer has. So eo_parent_set(obj, NULL) can free an object, and so
does eo_unref() (even if there is a parent).
This means Eo no longer complains if you have a parent during deletion.
So ecore main loop does restart everything with an main loop shutdown
and init when it detect a bad fd. This can happen if you del a fd after
you have destroyed it. Something terminology is doing (and should be
legal), but that then ended up with a main loop with no event handler
registered and the process was looking like stuck with nothing happening.
This fixes a crash in ecore_init, calling a weak function from
libefl that was resolved to NULL.
So, here's a fun thing happening with GCC < 5.3. Since a1a506e13e
all EOAPI and EO class_get() functions are weak symbols. This means
that all APIs inside libefl.so are weak.
As a result, gcc linker with --as-needed skipped linking to libefl
since not a single strong symbol from libefl was required by
libecore. This is actually a bug in gcc linker since we do in fact
use symbols from libefl, just weak ones.
GCC 5.3 seems to be fixed, so people with GCC 5.3+ will not
experience any build/runtime issue. The current patch is
a workaround that bug, by artifically creating a strong symbol
required by ecore.
Other libraries than ecore might also need to call
__efl_internal_init, if they end up not being linked to libefl.
this inits a new vpath object and adds it at priority 0 to the vpath
manager so you can use the vpath manager to create vpath file objects
and look things up.
@feature
Summary:
When glib support is enabled (HAVE_GLIB), _ecore_glib_init()
was always reserving resources. However, its counterpart may not
be called when:
- glib is not always integrated and
- when a user didn't explicitly required the integration.
Calling _ecore_glib_init() within the request code will cause the
resources to be reserved only when the integration with glib is
required and furthermore guarantees that resources always have a
chance to be released.
Reviewers: cedric, raster
Subscribers: cedric, jpeg
Differential Revision: https://phab.enlightenment.org/D3749
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
To configure efl sources with bindings to use in nodejs add ––with-js=nodejs in configure flags to generate node files
$ configure --with-js=nodejs
and compile normally with:
$ make
$ make install
To use, you have to require efl:
efl = require('efl')
The bindings is divided in two parts: generated and manually
written. The generation uses the Eolian library for parsing Eo files
and generate C++ code that is compiled against V8 interpreter library
to create a efl.node file that can be required in a node.js instance.
@feature
if you fork and even if you do ecore_fork_reset() a thread calling
ecore_main_loop_thread_safe_call_async(0 for example eill end up
resetting the mainloop thread id to itself (a non mainlopo thread) via
calling eina_main_loop_is() since pid changed. there is little point
in doing this so remove the pid tracking from eina and ensure mainloop
thread id is updated in ecore's fork reset.
@fix
This enable the possibility to block the main loop until a
specific thread is done. It may trigger still process ending
of other thread during that function call, but not any other
type of event (timer, animator, idler, ... are all ignored).
this makes efl ignore certain env vars for thnigs and entirely removes
user modules (that no one ever used) etc. etc. to ensure that *IF* an
app is setuid, there isn't a priv escalation path that is easy.