Merge branch 'master' into devs/hermet/lottie

This commit is contained in:
Hermet Park 2019-04-11 14:52:52 +09:00
commit e10f7b5c3d
184 changed files with 4590 additions and 1846 deletions

127
NEWS
View File

@ -5133,3 +5133,130 @@ Fixes:
- Fix memory leak in error case. - Fix memory leak in error case.
* Eeze: * Eeze:
- Fix sensors to not segv on shutdown. - Fix sensors to not segv on shutdown.
Changes since 1.21.0:
---------------------
Features:
* evas textblock: add/apply cursor cluster APIs based on grapheme cluster
* efl_ui_spin_button: Addded direction feature.
* scroller: refactory a momentum scroll animator
* elementary textpath: support legacy APIs
* elementary transit: add a convenient API.
* elementary transit: add a new api - elm_transit_progress_value_set()
* Text: add markup_range_get
* Canvas layout: support more Efl.Text.* with efl_part
* efl: Add support to elput for using elogind instead of systemd
* eina: add locale-independent eina_convert_strtod_c function
* elm perf tool - bring one back to efl
* eina: add locale-independent eina_convert_strtod_c function
* elm perf tool - bring one back to efl
* efl gfx_path: introduce efl_gfx_path_reserve()
* efl gfx_path: remove EFL_GFX_PATH_EVENT_CHANGED
* efl gfx_path: remove EFL_GFX_PATH_EVENT_CHANGED
* gfx: Add size hint fill (EO) (T3912)
* efl_app: add "standby" event (T5494)
* edje_cc: fail upon detecting invalid part description references in programs (T7016)
* elput: Add API to allow settings tap-to-click on pointer device
* ecore_drm2: Add API to allow settings tap-to-click on pointer device
* efl_ui_win: add 'exit_on_all_windows_closed' class property and unit test (T5494)
* efl_ui_win: add 'exit_on_close' property and unit test (T5494)
* eo: implement class overriding (+unit tests) (T7516)
* eolian gen: initial support for reflection api
* efl_ui_relative_layout: introduce new relative container (T5487)
* eolian: introduce typed slice types
* eolian: add support for inlist structs
* eolian: remove support for inlist/inarray
* ecore-drm2: Add API function to return output rotation (T7690)
Fixes:
* ecore_wl2_dmabuf: Link with ecore_wl2 (T7327)
* ecore_wl2_dmabuf: Depend on ecore_wl2 (T7327)
* efl selection manager - avoid multiple selection get callbacks for req
* evas image: fix a bug in image preloading.
* evas canvas: fix null possibility of evas_object_above_get().
* edje: Remove hack code
* efl gfx_path: prevent buffer overflow.
* ecore_main: fix the invalid return value
* eina_vpath: fix the memory leak
* elementary: remove meaningless memory allocation and leaking
* elementary: fix memory leak from Efl.Ui.Layout.Object
* evas gl: fix invalid image size.
* elementary entry: apply scale to all edje objects
* eina debug: fix a double unlock issue
* elm_theme: fix return value when default style fallback is done
* evas vg: fix memory leak.
* devas vg: return default root node if possible.
* evas vg: fix memory leak at gradient.
* evas filter: remove critical messages from Evas Filter
* elementary transit: fix wrong pausing time calculation.
* Canvas text: fix line_jump_by logic
* cxx: explicitly require c++11 and fix tests to conform
* edje: fix an overflow issue for state values
* evas textblock: remove white space after line-break by a next item
* evas ector: fix memory leaks.
* evas vg: update render properly.
* ector software: make a pair of ref/unref.
* evas gl: recover current program state.
* ecore_evas - fix aninmator based frame render ticking to full framerate
* ecore evas - buffer - init ecore event evas as many times as shutdown
* eina: fix a build failure caused by missing 'locale_t' from OSX
* ecore_con: handle timeout of the attempt to connect.
* ecore_evas - fix aninmator based frame render ticking to full framerate
* ecore evas - buffer - init ecore event evas as many times as shutdown
* eina: fix a build failure caused by missing 'locale_t' from OSX
* ecore_con: handle timeout of the attempt to connect.
* evas gl - make GLintptr etc. also ndefed for GL_VERSION_1_5 fix typedef (T7502)
* ecore-drm2: Fix drmModeSetCrtc call during fb flip
* textblock: Fix crash with filters
* edje - stop trying to access ready deleted exrt/group swallow objects
* evas: remove memory leaks from deleted Textblock objects
* elm - dnd - restore to working as drop targets
* elm_config: Free data returned from eet_read
* ui/flip: fix efl_pack usage
* elm_entry: make file loading succeed on 0-sized files (T6562)
* theme: fix odd state setting on some items for list/genlist/gengrid
* theme: correct part name in program for elm/hover/base/main_menu_submenu/default (T6219)
* theme: remove a ton of invalid part description references in various programs (T6873)
* ecore-evas/extn: use evas from events when updating key masks (T5536)
* edje: apply maps to textblock cursors and backgrounds (T4977)
* ecore drm2 - work around kms/drm bug seemingly when no flip event comes
* elm textpath: reduces differences between actual pos and modified pos
* elm_map: Make more robust elm_map (T7443)
* Fix leak in elm atspi
* eina_file: set errno on open fail for win32 build
* evas-gl-drm: Fix issue of rotation not actually rotating (T7690)
* solve neon rotation issue by moving to the tiled rotator
* eo: Fix missing varags cleanup (CID1399080)
* efl_core_command_line: Fix logically dead code (CID1399106)
* efl_ui_widget_common: Fix potential resource leak (CID1399088)
* efl_ui_selection_manager: Fix unchecked return value (CID1399092)
* evas_device: Fix dereferencing null pointer (CID1399091)
* efl_ui_stack: Fix dereference null return value (CID1399082)
* efl_ui_datepicker: Fix uninitialized scalar value (CID1397006)
* efl_ui_grid: Fix dereferencing null pointer (CID1397000)
* ecore_con: Fix dereferencing of null pointer (CID1396990)
* elm_atspi_bridge: Fix resource leak (CID1399429)
* efl_ui_win: Fix dereference null return value (CID1399428)
* efl_ui_win: Fix dereference null return (CID1399427)
* efl_ui_win: Fix dereference null return (CID1399426)
* efl_ui_win: Fix dereference null return value (CID1399425)
* efreet: Fix resource leak (CID1399090)
* efl_ui_text: Fix resource leak (CID1396998)
* eldbus: Fix dereference after null check (CID1399422)
* efl_ui_focus_manager_calc: Fix resource leaks (CID1396984, CID1396965)
* elm_focus_legacy: Fix resource leaks (CID1399096, CID1399095)
* eldbus: Fix resource leak (CID1399097)
* efl_canvas_vg_object: Fix dereference after null check (CID1399423, CID1399421)
* efl_ui_win: fix hw accel detection
* efl_ui_layout: Eina_Error type has been modified to work correctly.
* ecore-drm2: Don't use AtomicAddProperty for plane rotation (T7690)
* ecore-drm2: Update plane state values based on FB (T7690)
* ecore-drm2: Factor in output rotation when getting output info (T7690)
* evas drm: Don't use eng_output_resize or redraws clear (T7690)
* evas drm: Fix software output rotation (T7690)
* efl_ui_image: remove job in sizing calc. (T7360)
* evas_render: Process deferred callback in the sync render case.
* efl_ui_selection_manager: Don't leak malloc'd data (CID1396949)
* ecore-drm2: Add missing @ingroup for some doxy

View File

@ -1,5 +1,5 @@
EFL_VERSION([1], [22], [0], [release]) EFL_VERSION([1], [22], [99], [dev])
AC_INIT([efl], [efl_version-beta2], [enlightenment-devel@lists.sourceforge.net]) AC_INIT([efl], [efl_version], [enlightenment-devel@lists.sourceforge.net])
AC_PREREQ([2.60]) AC_PREREQ([2.60])
AC_CONFIG_SRCDIR([configure.ac]) AC_CONFIG_SRCDIR([configure.ac])
@ -1435,6 +1435,7 @@ EFL_LIB_START_OPTIONAL([Efl_Custom_Exports_Mono], [test "x${want_csharp}" = "xye
EFL_PLATFORM_DEPEND([EFL_CUSTOM_EXPORTS_MONO], [evil]) EFL_PLATFORM_DEPEND([EFL_CUSTOM_EXPORTS_MONO], [evil])
EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eina]) EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eina])
EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eo]) EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eo])
EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Ecore])
EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Efl]) EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Efl])
EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eldbus]) EFL_INTERNAL_DEPEND_PKG([EFL_CUSTOM_EXPORTS_MONO], [Eldbus])
@ -3259,7 +3260,7 @@ EFL_EVAL_PKGS([ECORE_CON])
### Checks for header files ### Checks for header files
AC_CHECK_HEADERS([ws2tcpip.h netdb.h sys/filio.h]) AC_CHECK_HEADERS([netdb.h sys/filio.h])
if test "x${ac_cv_header_netdb_h}" = "xno" && test "x${have_windows}" = "xno"; then if test "x${ac_cv_header_netdb_h}" = "xno" && test "x${have_windows}" = "xno"; then
AC_MSG_ERROR([netdb.h is requested to have Ecore_Con. Exiting...]) AC_MSG_ERROR([netdb.h is requested to have Ecore_Con. Exiting...])
@ -3267,18 +3268,19 @@ fi
### Checks for types ### Checks for types
have_ipv6="no" if test "x${have_win32}" = "xyes" ; then
AC_CHECK_TYPES([struct ipv6_mreq], have_ipv6="yes"
[have_ipv6="yes"], else
[have_ipv6="no"], have_ipv6="no"
[[ AC_CHECK_TYPES([struct ipv6_mreq],
[have_ipv6="yes"],
[have_ipv6="no"],
[[
#ifdef HAVE_NETINET_IN_H #ifdef HAVE_NETINET_IN_H
# include <netinet/in.h> # include <netinet/in.h>
#endif #endif
#ifdef HAVE_WS2TCPIP_H ]])
# include <ws2tcpip.h> fi
#endif
]])
AC_DEFINE_IF([HAVE_IPV6], AC_DEFINE_IF([HAVE_IPV6],
[test "x${have_ipv6}" = "xyes"], [test "x${have_ipv6}" = "xyes"],
@ -4117,7 +4119,6 @@ EFL_ADD_FEATURE([ECORE_AUDIO], [wasapiaudio])
EFL_LIB_END_OPTIONAL([Ecore_Audio]) EFL_LIB_END_OPTIONAL([Ecore_Audio])
AM_CONDITIONAL([HAVE_ECORE_AUDIO_PULSE], [test "x${want_pulseaudio}" = "xyes"]) AM_CONDITIONAL([HAVE_ECORE_AUDIO_PULSE], [test "x${want_pulseaudio}" = "xyes"])
AM_CONDITIONAL([HAVE_ECORE_AUDIO_SNDFILE], [test "x${want_sndfile}" = "xyes"]) AM_CONDITIONAL([HAVE_ECORE_AUDIO_SNDFILE], [test "x${want_sndfile}" = "xyes"])
AM_CONDITIONAL([HAVE_ECORE_AUDIO_WASASPI], [test "x${want_wasapiaudio}" = "xyes"])
#### End of Ecore_Audio #### End of Ecore_Audio

View File

@ -5,7 +5,7 @@ custom_target('edje_cc_edje_externals',
'-id', join_paths(meson.current_source_dir()), '-id', join_paths(meson.current_source_dir()),
'-id', elm_themes_image_include, '-id', elm_themes_image_include,
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, depends : edje_depends,
install : true, install : true,
install_dir : join_paths(dir_data, 'elementary', 'edje_externals'), install_dir : join_paths(dir_data, 'elementary', 'edje_externals'),
) )

View File

@ -26,7 +26,7 @@ foreach edc_file : edc_files
'-id', join_paths(meson.current_source_dir()), '-id', join_paths(meson.current_source_dir()),
'-fd', join_paths(meson.current_source_dir()), '-fd', join_paths(meson.current_source_dir()),
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, depends : edje_depends,
install : true, install : true,
install_dir : join_paths(dir_data, 'elementary', 'objects'), install_dir : join_paths(dir_data, 'elementary', 'objects'),
) )

View File

@ -18,7 +18,7 @@ foreach edc_file : edc_files
'-id', join_paths(meson.current_source_dir(), 'fdo'), '-id', join_paths(meson.current_source_dir(), 'fdo'),
'-fd', join_paths(meson.current_source_dir(), 'fnt'), '-fd', join_paths(meson.current_source_dir(), 'fnt'),
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, depends : edje_depends,
install : true, install : true,
install_dir : join_paths(dir_data, 'elementary', 'themes'), install_dir : join_paths(dir_data, 'elementary', 'themes'),
) )

View File

@ -8,7 +8,7 @@ custom_target('edje_cc_ethumb_frame',
'-id', join_paths(meson.current_source_dir()), '-id', join_paths(meson.current_source_dir()),
'-fd', join_paths(meson.current_source_dir()), '-fd', join_paths(meson.current_source_dir()),
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, depends : edje_depends,
install : true, install : true,
install_dir : join_paths(dir_data, 'ethumb', 'frames'), install_dir : join_paths(dir_data, 'ethumb', 'frames'),
) )

View File

@ -1,8 +1,10 @@
apiRules: apiRules:
- exclude: - exclude:
uidRegex: ^.*NativeInherit uidRegex: ^.*NativeInherit$
- exclude: - exclude:
uidRegex: ^.*Concrete uidRegex: ^.*NativeStruct$
- exclude:
uidRegex: ^.*Concrete$
- include: - include:
uidRegex: ^Efl uidRegex: ^Efl
- include: - include:

View File

@ -52,7 +52,6 @@ header_checks = [
'langinfo.h', 'langinfo.h',
'locale.h', 'locale.h',
'uv.h', 'uv.h',
'ws2tcpip.h',
'crt_externs.h' 'crt_externs.h'
] ]

View File

@ -1,5 +1,5 @@
project('efl', ['c','cpp'], project('efl', ['c','cpp'],
version: '1.22.0', version: '1.22.99',
default_options : ['buildtype=release', 'cpp_std=c++11'], default_options : ['buildtype=release', 'cpp_std=c++11'],
meson_version : '>=0.47' meson_version : '>=0.47'
) )

View File

@ -1,15 +1,18 @@
#!/bin/sh #!/bin/sh
original_loader=$1
filename="$(basename $original_loader)"
ext="${ext##*.}" ext="${ext##*.}"
original_name="$(basename $original_loader .$ext)" # skip trailing dot if any
loader_dir="$(dirname $original_loader)" case "$1" in
loader="$(basename $original_loader)" *.) original_loader=${1%?};;
loader_name="$(echo $original_name | cut -f 1 -d '.')" *) original_loader=$1;;
esac
original_name="$(basename "$original_loader")"
loader_dir="$(dirname "$original_loader")"
loader="$(basename "$original_loader")"
loader_name="$(echo "$loader" | cut -f 1 -d '.')"
if [ `echo -n ${original_loader} | tail -c 3` == "$ext" ] original_ext="$(echo "$loader" | tail -c 4)"
then if test "$original_ext" = "$ext" ; then
mv "$DESTDIR"/"$original_loader" "$DESTDIR"/"$loader_dir"/"$original_name" mv "$DESTDIR"/"$original_loader" "$DESTDIR"/"$loader_dir"/"$original_name"
fi fi

View File

@ -1,7 +1,7 @@
### Library ### Library
ecore_con_eolian_files = \ ecore_con_eolian_files_common = \
lib/ecore_con/efl_net_socket.eo \ lib/ecore_con/efl_net_socket.eo \
lib/ecore_con/efl_net_socket_simple.eo \ lib/ecore_con/efl_net_socket_simple.eo \
lib/ecore_con/efl_net_socket_fd.eo \ lib/ecore_con/efl_net_socket_fd.eo \
@ -30,16 +30,22 @@ ecore_con_eolian_files = \
lib/ecore_con/efl_net_session.eo \ lib/ecore_con/efl_net_session.eo \
lib/ecore_con/efl_net_ip_address.eo lib/ecore_con/efl_net_ip_address.eo
if HAVE_WINDOWS ecore_con_eolian_files_windows = \
ecore_con_eolian_files += \
lib/ecore_con/efl_net_socket_windows.eo \ lib/ecore_con/efl_net_socket_windows.eo \
lib/ecore_con/efl_net_dialer_windows.eo \ lib/ecore_con/efl_net_dialer_windows.eo \
lib/ecore_con/efl_net_server_windows.eo lib/ecore_con/efl_net_server_windows.eo
else
ecore_con_eolian_files += \ ecore_con_eolian_files_unix = \
lib/ecore_con/efl_net_socket_unix.eo \ lib/ecore_con/efl_net_socket_unix.eo \
lib/ecore_con/efl_net_dialer_unix.eo \ lib/ecore_con/efl_net_dialer_unix.eo \
lib/ecore_con/efl_net_server_unix.eo lib/ecore_con/efl_net_server_unix.eo
ecore_con_eolian_files = $(ecore_con_eolian_files_common)
if HAVE_WINDOWS
ecore_con_eolian_files += $(ecore_con_eolian_files_windows)
else
ecore_con_eolian_files += $(ecore_con_eolian_files_unix)
endif endif
ecore_con_eolian_type_files = \ ecore_con_eolian_type_files = \
@ -64,8 +70,10 @@ ecoreconeolianfiles_DATA = \
endif endif
EXTRA_DIST2 += \ EXTRA_DIST2 += \
$(ecore_con_eolian_files) \ $(ecore_con_eolian_files_common) \
$(ecore_con_eolian_type_files) $(ecore_con_eolian_files_unix) \
$(ecore_con_eolian_files_windows) \
$(ecore_con_eolian_type_files)
lib_LTLIBRARIES += lib/ecore_con/libecore_con.la lib_LTLIBRARIES += lib/ecore_con/libecore_con.la

View File

@ -206,6 +206,8 @@ $(efl_eolian_type_files:%.eot=%.eot.cs) \
$(edje_eolian_type_files:%.eot=%.eot.cs) \ $(edje_eolian_type_files:%.eot=%.eot.cs) \
$(elm_eolian_type_files:%.eot=%.eot.cs) \ $(elm_eolian_type_files:%.eot=%.eot.cs) \
$(filter-out $(evas_eolian_blacklisted_files),$(evas_canvas_eolian_pub_files:%.eo=%.eo.cs)) \ $(filter-out $(evas_eolian_blacklisted_files),$(evas_canvas_eolian_pub_files:%.eo=%.eo.cs)) \
$(evas_gesture_eolian_pub_files:%.eo=%.eo.cs) \
$(evas_gesture_eolian_type_files:%.eot=%.eot.cs) \
lib/evas/canvas/efl_canvas_image.eo.cs \ lib/evas/canvas/efl_canvas_image.eo.cs \
$(evas_canvas_eolian_type_files:%.eot=%.eot.cs) \ $(evas_canvas_eolian_type_files:%.eot=%.eot.cs) \
lib/eo/eina_types.eot.cs \ lib/eo/eina_types.eot.cs \
@ -493,9 +495,15 @@ tests_efl_mono_efl_mono_SOURCES = \
tests/efl_mono/EinaTestData.cs \ tests/efl_mono/EinaTestData.cs \
tests/efl_mono/StructHelpers.cs tests/efl_mono/StructHelpers.cs
beta_mono_flags =
if HAVE_CSHARP_BETA
beta_mono_flags += -define:EFL_BETA
endif
tests/efl_mono/efl_mono$(EXEEXT): $(tests_efl_mono_efl_mono_SOURCES) tests/efl_mono/$(am__dirstamp) lib/efl_mono/libefl_mono.dll tests/efl_mono/libefl_mono_test.dll tests/efl_mono/efl_mono$(EXEEXT).config tests/efl_mono/efl_mono$(EXEEXT): $(tests_efl_mono_efl_mono_SOURCES) tests/efl_mono/$(am__dirstamp) lib/efl_mono/libefl_mono.dll tests/efl_mono/libefl_mono_test.dll tests/efl_mono/efl_mono$(EXEEXT).config
@rm -f $@ @rm -f $@
$(AM_V_MCS) $(MCS) $(MCSFLAGS) -r:$(abs_top_builddir)/src/lib/efl_mono/libefl_mono.dll -r:$(abs_top_builddir)/src/tests/efl_mono/libefl_mono_test.dll -out:$@ $(filter %.cs, $(^)) $(AM_V_MCS) $(MCS) $(MCSFLAGS) -r:$(abs_top_builddir)/src/lib/efl_mono/libefl_mono.dll -r:$(abs_top_builddir)/src/tests/efl_mono/libefl_mono_test.dll -out:$@ $(filter %.cs, $(^)) $(beta_mono_flags)
# Rule for generating the .cs files # Rule for generating the .cs files
tests/efl_mono/%.eo.cs: tests/efl_mono/%.eo $(_EOLIAN_MONO_DEP) tests/efl_mono/%.eo.cs: tests/efl_mono/%.eo $(_EOLIAN_MONO_DEP)

View File

@ -1819,6 +1819,8 @@ edje_external_elementary_module_la_LIBTOOLFLAGS = --tag=disable-static
testfilesdir = $(datadir)/elementary/ testfilesdir = $(datadir)/elementary/
testfiles_DATA = \ testfiles_DATA = \
tests/elementary/testfile_entry.txt \
tests/elementary/testfile_entry2.txt \
tests/elementary/testfile.txt \ tests/elementary/testfile.txt \
tests/elementary/testfile-windows.txt \ tests/elementary/testfile-windows.txt \
tests/elementary/testfile-withblanks.txt \ tests/elementary/testfile-withblanks.txt \
@ -1944,6 +1946,7 @@ tests_elementary_efl_ui_suite_SOURCES = \
tests/elementary/efl_ui_build.c \ tests/elementary/efl_ui_build.c \
tests/elementary/elm_test_init.c \ tests/elementary/elm_test_init.c \
tests/elementary/efl_ui_test_atspi.c \ tests/elementary/efl_ui_test_atspi.c \
tests/elementary/efl_ui_test_callback.c \
tests/elementary/efl_ui_test_focus_common.c \ tests/elementary/efl_ui_test_focus_common.c \
tests/elementary/efl_ui_test_focus_common.h \ tests/elementary/efl_ui_test_focus_common.h \
tests/elementary/efl_ui_test_focus.c \ tests/elementary/efl_ui_test_focus.c \
@ -2014,4 +2017,4 @@ lib/elementary/elm_code_widget_undo.c \
lib/elementary/config_embed lib/elementary/config_embed
lib/elementary/elm_default_config.x: lib/elementary/elm_default_config.x:
lib/elementary/config_embed $(abs_top_srcdir)/data/elementary/config/standard/base.src.in $@ $(top_srcdir)/src/lib/elementary/config_embed $(abs_top_srcdir)/data/elementary/config/standard/base.src.in $@

View File

@ -64,11 +64,11 @@ modules/ethumb/emotion/template.edj: modules/ethumb/emotion/template.edc modules
ethumbmoduleemotion_DATA = modules/ethumb/emotion/template.edj ethumbmoduleemotion_DATA = modules/ethumb/emotion/template.edj
CLEANFILES += modules/ethumb/emotion/template.edj CLEANFILES += modules/ethumb/emotion/template.edj
endif
EXTRA_DIST2 += \ EXTRA_DIST2 += \
modules/ethumb/emotion/template.edc \ modules/ethumb/emotion/template.edc \
modules/ethumb/emotion/placeholder.png modules/ethumb/emotion/placeholder.png
endif
### Binary ### Binary

View File

@ -2284,6 +2284,7 @@ tests/evas/evas_suite.h
tests_evas_evas_suite_CPPFLAGS = -I$(top_builddir)/src/lib/efl \ tests_evas_evas_suite_CPPFLAGS = -I$(top_builddir)/src/lib/efl \
-I$(top_srcdir)/src/lib/ecore_evas \ -I$(top_srcdir)/src/lib/ecore_evas \
-I$(top_builddir)/src/lib/evas/canvas \ -I$(top_builddir)/src/lib/evas/canvas \
-I$(top_srcdir)/src/modules/evas/engines/buffer \
-DPACKAGE_BUILD_DIR=\"$(abs_top_builddir)\" \ -DPACKAGE_BUILD_DIR=\"$(abs_top_builddir)\" \
-DTESTS_SRC_DIR=\"$(top_srcdir)/src/tests/evas\" \ -DTESTS_SRC_DIR=\"$(top_srcdir)/src/tests/evas\" \
-DTESTS_BUILD_DIR=\"$(top_builddir)/src/tests/evas\" \ -DTESTS_BUILD_DIR=\"$(top_builddir)/src/tests/evas\" \

View File

@ -91,6 +91,7 @@ tests/evil/evil_test_unistd.c
tests_evil_evil_suite_CPPFLAGS = \ tests_evil_evil_suite_CPPFLAGS = \
-I$(top_builddir)/src/lib/efl \ -I$(top_builddir)/src/lib/efl \
-I$(top_builddir)/src/lib/eina \
-DTESTS_SRC_DIR=\"$(top_srcdir)/src/tests/evil\" \ -DTESTS_SRC_DIR=\"$(top_srcdir)/src/tests/evil\" \
-DPACKAGE_BUILD_DIR=\"$(abs_top_builddir)/\" \ -DPACKAGE_BUILD_DIR=\"$(abs_top_builddir)/\" \
-DTESTS_BUILD_DIR=\"$(top_builddir)/src/tests/evil\" \ -DTESTS_BUILD_DIR=\"$(top_builddir)/src/tests/evil\" \

View File

@ -28,12 +28,16 @@
#define EDJE_1_19_SUPPORTED " -DEFL_VERSION_1_19=1 " #define EDJE_1_19_SUPPORTED " -DEFL_VERSION_1_19=1 "
#define EDJE_1_20_SUPPORTED " -DEFL_VERSION_1_20=1 " #define EDJE_1_20_SUPPORTED " -DEFL_VERSION_1_20=1 "
#define EDJE_1_21_SUPPORTED " -DEFL_VERSION_1_21=1 " #define EDJE_1_21_SUPPORTED " -DEFL_VERSION_1_21=1 "
#define EDJE_1_22_SUPPORTED " -DEFL_VERSION_1_22=1 "
#define EDJE_1_23_SUPPORTED " -DEFL_VERSION_1_23=1 "
#define EDJE_CC_EFL_VERSION_SUPPORTED \ #define EDJE_CC_EFL_VERSION_SUPPORTED \
EDJE_1_18_SUPPORTED \ EDJE_1_18_SUPPORTED \
EDJE_1_19_SUPPORTED \ EDJE_1_19_SUPPORTED \
EDJE_1_20_SUPPORTED \ EDJE_1_20_SUPPORTED \
EDJE_1_21_SUPPORTED EDJE_1_21_SUPPORTED \
EDJE_1_22_SUPPORTED \
EDJE_1_23_SUPPORTED
static void new_object(void); static void new_object(void);
static void new_statement(void); static void new_statement(void);

View File

@ -34,9 +34,11 @@ if meson.is_cross_build()
_edje_cc = find_program('edje_cc', native: true) _edje_cc = find_program('edje_cc', native: true)
edje_cc_path = _edje_cc.path() edje_cc_path = _edje_cc.path()
edje_cc_exe = [_edje_cc] edje_cc_exe = [_edje_cc]
edje_depends = []
else else
env = find_program('env', native: true) env = find_program('env', native: true)
edje_cc_exe = [env, 'EFL_RUN_IN_TREE=1', edje_cc.full_path()] edje_cc_exe = [env, 'EFL_RUN_IN_TREE=1', edje_cc.full_path()]
edje_depends = [edje_cc, epp]
endif endif
edje_decc_src = [ edje_decc_src = [

View File

@ -20,6 +20,7 @@
#include "efreetd_ipc.h" #include "efreetd_ipc.h"
int efreetd_log_dom = -1; int efreetd_log_dom = -1;
Eina_Mempool *efreetd_mp_stat = NULL;
void void
quit(void) quit(void)

View File

@ -1,7 +1,7 @@
#ifndef __EFREETD_CACHE_H #ifndef __EFREETD_CACHE_H
#define __EFREETD_CACHE_H #define __EFREETD_CACHE_H
Eina_Mempool *efreetd_mp_stat; extern Eina_Mempool *efreetd_mp_stat;
void cache_desktop_dir_add(const char *dir); void cache_desktop_dir_add(const char *dir);
void cache_icon_dir_add(const char *dir); void cache_icon_dir_add(const char *dir);

View File

@ -36,8 +36,7 @@ typedef enum _Pack_Type {
PACK_BEFORE, PACK_BEFORE,
PACK_AFTER, PACK_AFTER,
PACK_AT, PACK_AT,
UNPACK_AT, UNPACK_AT
CLEAR
} Pack_Type; } Pack_Type;
typedef struct _Params { typedef struct _Params {
@ -219,7 +218,7 @@ static void pack_btn_cb(void *data, const Efl_Event *ev EINA_UNUSED)
Eo *page = NULL, *curr_page; Eo *page = NULL, *curr_page;
int index, cnt; int index, cnt;
if ((param->type != UNPACK_AT) && (param->type != CLEAR)) { if (param->type != UNPACK_AT) {
index = efl_content_count(pager); index = efl_content_count(pager);
switch (index % 3) { switch (index % 3) {
@ -261,12 +260,10 @@ static void pack_btn_cb(void *data, const Efl_Event *ev EINA_UNUSED)
break; break;
case UNPACK_AT: case UNPACK_AT:
index = efl_ui_range_value_get(param->unpack_sp); index = efl_ui_range_value_get(param->unpack_sp);
page = efl_pack_unpack_at(pager, index); page = efl_pack_content_get(pager, index);
efl_pack_unpack(pager, page);
efl_del(page); efl_del(page);
break; break;
case CLEAR:
efl_pack_clear(pager);
break;
} }
cnt = efl_content_count(pager); cnt = efl_content_count(pager);
@ -590,25 +587,6 @@ static void pack_cb(void *data,
efl_pack_end(box, in_box2); efl_pack_end(box, in_box2);
efl_pack_end(in_box2, btn); efl_pack_end(in_box2, btn);
efl_pack_end(in_box2, sp2); efl_pack_end(in_box2, sp2);
// Clear
pack_param = calloc(1, sizeof(Pack_Params));
if (!pack_param) return;
pack_param->pager = pager;
pack_param->pack_sp = sp1;
pack_param->unpack_sp = sp2;
pack_param->unpack_btn = btn;
pack_param->type = CLEAR;
efl_add(EFL_UI_BUTTON_CLASS, box,
efl_text_set(efl_added, "Clear"),
efl_event_callback_add(efl_added, EFL_UI_EVENT_CLICKED,
pack_btn_cb, pack_param),
efl_event_callback_add(efl_added, EFL_EVENT_DEL,
pack_btn_del_cb, pack_param),
efl_pack_end(box, efl_added));
} }
static void current_page_cb(void *data, static void current_page_cb(void *data,

View File

@ -36,8 +36,7 @@ typedef enum _Pack_Type {
PACK_BEFORE, PACK_BEFORE,
PACK_AFTER, PACK_AFTER,
PACK_AT, PACK_AT,
UNPACK_AT, UNPACK_AT
CLEAR
} Pack_Type; } Pack_Type;
typedef struct _Params { typedef struct _Params {
@ -241,7 +240,7 @@ static void pack_btn_cb(void *data, const Efl_Event *ev EINA_UNUSED)
Eo *page = NULL, *curr_page; Eo *page = NULL, *curr_page;
int index, cnt; int index, cnt;
if ((param->type != UNPACK_AT) && (param->type != CLEAR)) { if (param->type != UNPACK_AT) {
index = efl_content_count(pager); index = efl_content_count(pager);
switch (index % 3) { switch (index % 3) {
@ -283,12 +282,10 @@ static void pack_btn_cb(void *data, const Efl_Event *ev EINA_UNUSED)
break; break;
case UNPACK_AT: case UNPACK_AT:
index = efl_ui_range_value_get(param->unpack_sp); index = efl_ui_range_value_get(param->unpack_sp);
page = efl_pack_unpack_at(pager, index); page = efl_pack_content_get(pager, index);
efl_pack_unpack(pager, page);
efl_del(page); efl_del(page);
break; break;
case CLEAR:
efl_pack_clear(pager);
break;
} }
cnt = efl_content_count(pager); cnt = efl_content_count(pager);
@ -356,11 +353,13 @@ static void next_block_check_cb(void *data, const Efl_Event *ev)
efl_ui_pager_scroll_block_set(pager, prev, next); efl_ui_pager_scroll_block_set(pager, prev, next);
} }
static void loop_radio_cb(void *data, const Efl_Event *ev) static void loop_check_cb(void *data, const Efl_Event *ev)
{ {
Eo *pager = data; Eo *pager = data;
int state = efl_ui_nstate_value_get(ev->object); int state = efl_ui_nstate_value_get(ev->object);
//FIXME use other widget (i.e. radio) than check
// since loop might not be enabled according to the number of items
efl_ui_pager_loop_mode_set(pager, state); efl_ui_pager_loop_mode_set(pager, state);
} }
@ -702,24 +701,6 @@ static void pack_cb(void *data,
efl_pack_end(box, in_box2); efl_pack_end(box, in_box2);
efl_pack_end(in_box2, btn); efl_pack_end(in_box2, btn);
efl_pack_end(in_box2, sp2); efl_pack_end(in_box2, sp2);
// Clear
pack_param = calloc(1, sizeof(Pack_Params));
if (!pack_param) return;
pack_param->pager = pager;
pack_param->pack_sp = sp1;
pack_param->unpack_sp = sp2;
pack_param->unpack_btn = btn;
pack_param->type = CLEAR;
efl_add(EFL_UI_BUTTON_CLASS, box,
efl_text_set(efl_added, "Clear"),
efl_event_callback_add(efl_added, EFL_UI_EVENT_CLICKED,
pack_btn_cb, pack_param),
efl_event_callback_add(efl_added, EFL_EVENT_DEL,
pack_btn_del_cb, pack_param),
efl_pack_end(box, efl_added));
} }
static void current_page_cb(void *data, static void current_page_cb(void *data,
@ -817,8 +798,7 @@ static void loop_cb(void *data EINA_UNUSED,
Params *params = (Params *)data; Params *params = (Params *)data;
Evas_Object *navi = params->navi; Evas_Object *navi = params->navi;
Eo *pager = params->pager; Eo *pager = params->pager;
Eo *btn, *box, *rd; Eo *btn, *box;
Efl_Ui_Pager_Loop loop;
btn = efl_add(EFL_UI_BUTTON_CLASS, navi, btn = efl_add(EFL_UI_BUTTON_CLASS, navi,
efl_text_set(efl_added, "Back"), efl_text_set(efl_added, "Back"),
@ -830,35 +810,13 @@ static void loop_cb(void *data EINA_UNUSED,
elm_naviframe_item_push(navi, "Loop", btn, NULL, elm_naviframe_item_push(navi, "Loop", btn, NULL,
efl_added, NULL)); efl_added, NULL));
rd = efl_add(EFL_UI_RADIO_CLASS, box, efl_add(EFL_UI_CHECK_CLASS, box,
efl_ui_radio_state_value_set(efl_added, EFL_UI_PAGER_LOOP_DISABLED), efl_ui_widget_style_set(efl_added, "toggle"),
efl_text_set(efl_added, "Disabled"), efl_text_set(efl_added, "Loop"),
efl_gfx_hint_weight_set(efl_added, 1, 0), efl_ui_nstate_value_set(efl_added, efl_ui_pager_loop_mode_get(pager)),
efl_event_callback_add(efl_added, EFL_UI_RADIO_EVENT_CHANGED, efl_event_callback_add(efl_added, EFL_UI_CHECK_EVENT_CHANGED,
loop_radio_cb, pager), loop_check_cb, pager),
efl_pack(box, efl_added)); efl_pack_end(box, efl_added));
rd = efl_add(EFL_UI_RADIO_CLASS, box,
efl_ui_radio_state_value_set(efl_added, EFL_UI_PAGER_LOOP_ENABLED),
efl_ui_radio_group_add(efl_added, rd),
efl_text_set(efl_added, "Enabled"),
efl_gfx_hint_weight_set(efl_added, 1, 0),
efl_event_callback_add(efl_added, EFL_UI_RADIO_EVENT_CHANGED,
loop_radio_cb, pager),
efl_pack(box, efl_added));
loop = efl_ui_pager_loop_mode_get(pager);
efl_ui_nstate_value_set(rd, loop);
if (loop == EFL_UI_PAGER_LOOP_DISABLED)
{
Eina_Bool ret = efl_ui_pager_loop_mode_set(pager, EFL_UI_PAGER_LOOP_ENABLED);
if (!ret)
elm_object_disabled_set(rd, EINA_TRUE);
else
efl_ui_pager_loop_mode_set(pager, EFL_UI_PAGER_LOOP_DISABLED);
}
} }
static void indicator_cb(void *data EINA_UNUSED, static void indicator_cb(void *data EINA_UNUSED,

View File

@ -16,6 +16,7 @@ inline bool is_function_blacklisted(std::string const& c_name)
{ {
return return
c_name == "efl_event_callback_array_priority_add" c_name == "efl_event_callback_array_priority_add"
|| c_name == "efl_constructor"
|| c_name == "efl_player_position_get" || c_name == "efl_player_position_get"
|| c_name == "efl_ui_widget_focus_set" || c_name == "efl_ui_widget_focus_set"
|| c_name == "efl_ui_widget_focus_get" || c_name == "efl_ui_widget_focus_get"

View File

@ -30,7 +30,7 @@ struct unpack_event_args_visitor
// Structs are usually passed by pointer to events, like having a ptr<> modifier // Structs are usually passed by pointer to events, like having a ptr<> modifier
// Uses implicit conversion from IntPtr // Uses implicit conversion from IntPtr
return as_generator( return as_generator(
" evt.Info;" " evt.Info"
).generate(sink, attributes::unused, *context); ).generate(sink, attributes::unused, *context);
} }
else if (type.is_ptr) else if (type.is_ptr)
@ -73,7 +73,7 @@ struct unpack_event_args_visitor
} }
bool operator()(grammar::attributes::klass_name const& cls) const bool operator()(grammar::attributes::klass_name const& cls) const
{ {
return as_generator("new " + name_helpers::klass_full_concrete_name(cls) + "(evt.Info)").generate(sink, attributes::unused, *context); return as_generator("(Efl.Eo.Globals.CreateWrapperFor(evt.Info) as " + name_helpers::klass_full_concrete_name(cls) + ")").generate(sink, attributes::unused, *context);
} }
bool operator()(attributes::complex_type_def const&) const bool operator()(attributes::complex_type_def const&) const
{ {
@ -81,6 +81,116 @@ struct unpack_event_args_visitor
} }
}; };
template<typename OutputIterator, typename Context>
struct pack_event_info_and_call_visitor
{
mutable OutputIterator sink;
Context const* context;
attributes::type_def const& type;
static auto constexpr native_call = "Efl.Eo.Globals.efl_event_callback_call(this.NativeHandle, desc, info);\n";
typedef pack_event_info_and_call_visitor<OutputIterator, Context> visitor_type;
typedef bool result_type;
bool operator()(grammar::attributes::regular_type_def const& regular) const
{
std::string arg_type = name_helpers::type_full_managed_name(regular);
auto const& indent = current_indentation(*context);
if (regular.is_struct())
{
return as_generator(
indent << "IntPtr info = Marshal.AllocHGlobal(Marshal.SizeOf(e.arg));\n"
<< indent << "try\n"
<< indent << "{\n"
<< indent << scope_tab << "Marshal.StructureToPtr(e.arg, info, false);\n"
<< indent << scope_tab << this->native_call
<< indent << "}\n"
<< indent << "finally\n"
<< indent << "{\n"
<< indent << scope_tab << "Marshal.FreeHGlobal(info);\n"
<< indent << "}\n"
).generate(sink, attributes::unused, *context);
}
using attributes::regular_type_def;
struct match
{
eina::optional<std::string> name;
std::function<std::string()> function;
};
std::string full_type_name = name_helpers::type_full_eolian_name(regular);
auto filter_func = [&regular, &full_type_name] (match const& m)
{
return (!m.name || *m.name == regular.base_type || *m.name == full_type_name);
};
match const str_table[] =
{
{"string", [] { return "e.arg"; }}
, {"stringshare", [] { return "e.arg"; }}
};
auto str_accept_func = [&](std::string const& conversion)
{
return as_generator(
indent << "IntPtr info = Eina.StringConversion.ManagedStringToNativeUtf8Alloc(" << conversion << ");\n"
<< indent << "try\n"
<< indent << "{\n"
<< indent << scope_tab << this->native_call
<< indent << "}\n"
<< indent << "finally\n"
<< indent << "{\n"
<< indent << scope_tab << "Eina.MemoryNative.Free(info);\n"
<< indent << "}\n").generate(sink, attributes::unused, *context);
};
if (eina::optional<bool> b = call_match(str_table, filter_func, str_accept_func))
return *b;
match const value_table [] =
{
{"bool", [] { return "e.arg ? (byte) 1 : (byte) 0"; }}
, {"Eina.Error", [] { return "(int)e.arg"; }}
, {nullptr, [] { return "e.arg"; }}
};
auto value_accept_func = [&](std::string const& conversion)
{
return as_generator(
indent << "IntPtr info = Eina.PrimitiveConversion.ManagedToPointerAlloc(" << conversion << ");\n"
<< indent << "try\n"
<< indent << "{\n"
<< indent << scope_tab << this->native_call
<< indent << "}\n"
<< indent << "finally\n"
<< indent << "{\n"
<< indent << scope_tab << "Marshal.FreeHGlobal(info);\n"
<< indent << "}\n").generate(sink, attributes::unused, *context);
};
if (eina::optional<bool> b = call_match(value_table, filter_func, value_accept_func))
return *b;
return value_accept_func("e.args");
}
bool operator()(grammar::attributes::klass_name const&) const
{
auto const& indent = current_indentation(*context);
return as_generator(indent << "IntPtr info = e.arg.NativeHandle;\n"
<< indent << this->native_call).generate(sink, attributes::unused, *context);
}
bool operator()(attributes::complex_type_def const&) const
{
auto const& indent = current_indentation(*context);
return as_generator(indent << "IntPtr info = e.arg.Handle;\n"
<< indent << this->native_call).generate(sink, attributes::unused, *context);
}
};
/* /*
* Generates a struct wrapping the argument of a given event. * Generates a struct wrapping the argument of a given event.
*/ */
@ -138,40 +248,6 @@ struct event_declaration_generator
} }
} const event_declaration {}; } const event_declaration {};
struct event_registration_generator
{
attributes::klass_def const& klass;
attributes::klass_def const& leaf_klass;
bool is_inherited_event;
template<typename OutputIterator, typename Context>
bool generate(OutputIterator sink, attributes::event_def const& evt, Context const& context) const
{
std::string wrapper_event_name;
if (blacklist::is_event_blacklisted(evt, context))
return true;
if (is_inherited_event && !helpers::is_unique_event(evt, leaf_klass))
wrapper_event_name = name_helpers::translate_inherited_event_name(evt, klass);
else
wrapper_event_name = name_helpers::managed_event_name(evt.name);
return as_generator(scope_tab << scope_tab << "evt_" << wrapper_event_name << "_delegate = "
<< "new Efl.EventCb(on_" << wrapper_event_name << "_NativeCallback);\n"
).generate(sink, attributes::unused, context);
}
};
struct event_registration_parameterized
{
event_registration_generator operator()(attributes::klass_def const& klass, attributes::klass_def const& leaf_klass) const
{
bool is_inherited_event = klass != leaf_klass;
return {klass, leaf_klass, is_inherited_event};
}
} const event_registration;
struct event_definition_generator struct event_definition_generator
{ {
attributes::klass_def const& klass; attributes::klass_def const& klass;
@ -185,6 +261,7 @@ struct event_definition_generator
return true; return true;
std::string managed_evt_name = name_helpers::managed_event_name(evt.name); std::string managed_evt_name = name_helpers::managed_event_name(evt.name);
auto const& indent = current_indentation(context);
bool is_unique = helpers::is_unique_event(evt, leaf_klass); bool is_unique = helpers::is_unique_event(evt, leaf_klass);
bool use_explicit_impl = is_inherited_event && !is_unique; bool use_explicit_impl = is_inherited_event && !is_unique;
@ -205,20 +282,35 @@ struct event_definition_generator
std::string wrapper_args_type = "EventArgs"; std::string wrapper_args_type = "EventArgs";
std::string wrapper_args_template = ""; std::string wrapper_args_template = "";
std::string event_args = "EventArgs args = EventArgs.Empty;\n"; std::string event_args = "EventArgs args = EventArgs.Empty;\n";
std::string event_native_call;
efl::eina::optional<grammar::attributes::type_def> etype = evt.type; efl::eina::optional<grammar::attributes::type_def> etype = evt.type;
if (etype.is_engaged()) if (!etype.is_engaged())
{
auto event_call_site_sink = std::back_inserter(event_native_call);
if (!as_generator(indent.inc().inc() << "Efl.Eo.Globals.efl_event_callback_call(this.NativeHandle, desc, IntPtr.Zero);\n")
.generate(event_call_site_sink, attributes::unused, context))
return false;
}
else
{ {
wrapper_args_type = name_helpers::managed_event_args_name(evt); wrapper_args_type = name_helpers::managed_event_args_name(evt);
wrapper_args_template = "<" + wrapper_args_type + ">"; wrapper_args_template = "<" + wrapper_args_type + ">";
std::string arg_initializer = wrapper_args_type + " args = new " + wrapper_args_type + "();\n"; std::string arg_initializer;
arg_initializer += " args.arg = ";
auto arg_initializer_sink = std::back_inserter(arg_initializer); auto arg_initializer_sink = std::back_inserter(arg_initializer);
auto event_call_site_sink = std::back_inserter(event_native_call);
if (!(*etype).original_type.visit(unpack_event_args_visitor<decltype(arg_initializer_sink), Context>{arg_initializer_sink, &context, *etype})) auto sub_context = change_indentation(indent.inc().inc(), context);
if (!as_generator(scope_tab(6) << wrapper_args_type << " args = new " << wrapper_args_type << "();\n"
<< scope_tab(6) << "args.arg = ").generate(arg_initializer_sink, attributes::unused, context))
return false;
if (!(*etype).original_type.visit(unpack_event_args_visitor<decltype(arg_initializer_sink), decltype(sub_context)>{arg_initializer_sink, &sub_context, *etype}))
return false;
if (!(*etype).original_type.visit(pack_event_info_and_call_visitor<decltype(event_call_site_sink), decltype(sub_context)>{event_call_site_sink, &sub_context, *etype}))
return false; return false;
arg_initializer += ";\n"; arg_initializer += ";\n";
@ -226,10 +318,6 @@ struct event_definition_generator
event_args = arg_initializer; event_args = arg_initializer;
} }
if(!as_generator("private static object " << wrapper_evt_name << "Key = new object();\n")
.generate(sink, attributes::unused, context))
return false;
if(!as_generator(documentation(1)).generate(sink, evt, context)) if(!as_generator(documentation(1)).generate(sink, evt, context))
return false; return false;
@ -256,31 +344,10 @@ struct event_definition_generator
return false; return false;
} }
if (!generate_event_add_remove(sink, evt, wrapper_evt_name, context)) if (!generate_event_add_remove(sink, evt, event_args, context))
return false; return false;
if (!generate_event_trigger(sink, wrapper_evt_name, wrapper_args_type, wrapper_args_template, context)) if (!generate_event_trigger(sink, evt, wrapper_evt_name, wrapper_args_type, event_native_call, context))
return false;
// Store the delegate for this event in this instance. This is initialized in RegisterEventProxies()
// We can't initialize them directly here as they depend on the member methods being valid (i.e.
// the constructor being called).
if (!as_generator(scope_tab << "Efl.EventCb evt_" << wrapper_evt_name << "_delegate;\n").generate(sink, attributes::unused, context))
return false;
// Callback to be given to C's callback_priority_add
if (!as_generator(
scope_tab << "private void on_" << wrapper_evt_name << "_NativeCallback(System.IntPtr data, ref Efl.Event.NativeStruct evt)\n"
<< scope_tab << "{\n"
<< scope_tab << scope_tab << event_args
<< scope_tab << scope_tab << "try {\n"
<< scope_tab << scope_tab << scope_tab << "On_" << wrapper_evt_name << "(args);\n"
<< scope_tab << scope_tab << "} catch (Exception e) {\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Log.Error(e.ToString());\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Error.Set(Eina.Error.UNHANDLED_EXCEPTION);\n"
<< scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n\n"
).generate(sink, attributes::unused, context))
return false; return false;
return true; return true;
@ -288,21 +355,26 @@ struct event_definition_generator
template<typename OutputIterator, typename Context> template<typename OutputIterator, typename Context>
bool generate_event_trigger(OutputIterator sink bool generate_event_trigger(OutputIterator sink
, attributes::event_def const &evt
, std::string const& event_name , std::string const& event_name
, std::string const& event_args_type , std::string const& event_args_type
, std::string const& event_template_args , std::string const& event_native_call
, Context const& context) const , Context const& context) const
{ {
auto delegate_type = "EventHandler" + event_template_args; auto library_name = context_find_tag<library_context>(context).actual_library_name(klass.filename);
std::string upper_c_name = utils::to_uppercase(evt.c_name);
if (!as_generator( if (!as_generator(
scope_tab << "///<summary>Method to raise event "<< event_name << ".</summary>\n" scope_tab << "///<summary>Method to raise event "<< event_name << ".</summary>\n"
<< scope_tab << "public void On_" << event_name << "(" << event_args_type << " e)\n" << scope_tab << "public void On" << event_name << "(" << event_args_type << " e)\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << delegate_type << " evt;\n" << scope_tab << scope_tab << "var key = \"_" << upper_c_name << "\";\n"
<< scope_tab << scope_tab << "lock (eventLock) {\n" << scope_tab << scope_tab << "IntPtr desc = Efl.EventDescription.GetNative(" << library_name << ", key);\n"
<< scope_tab << scope_tab << "evt = (" << delegate_type << ")eventHandlers[" << event_name << "Key];\n" << scope_tab << scope_tab << "if (desc == IntPtr.Zero)\n"
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << "evt?.Invoke(this, e);\n" << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to get native event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << "return;\n"
<< scope_tab << scope_tab << "}\n\n"
<< event_native_call
<< scope_tab << "}\n" << scope_tab << "}\n"
).generate(sink, nullptr, context)) ).generate(sink, nullptr, context))
return false; return false;
@ -311,7 +383,10 @@ struct event_definition_generator
} }
template<typename OutputIterator, typename Context> template<typename OutputIterator, typename Context>
bool generate_event_add_remove(OutputIterator sink, attributes::event_def const &evt, const std::string& event_name, Context const& context) const bool generate_event_add_remove(OutputIterator sink
, attributes::event_def const &evt
, std::string const& event_args
, Context const& context) const
{ {
std::string upper_c_name = utils::to_uppercase(evt.c_name); std::string upper_c_name = utils::to_uppercase(evt.c_name);
auto unit = (const Eolian_Unit*) context_find_tag<eolian_state_context>(context).state; auto unit = (const Eolian_Unit*) context_find_tag<eolian_state_context>(context).state;
@ -319,22 +394,38 @@ struct event_definition_generator
auto library_name = context_find_tag<library_context>(context).actual_library_name(klass.filename); auto library_name = context_find_tag<library_context>(context).actual_library_name(klass.filename);
return as_generator( return as_generator(
scope_tab << "{\n" scope_tab << "{\n"
<< scope_tab << scope_tab << "add {\n" << scope_tab << scope_tab << "add\n"
<< scope_tab << scope_tab << scope_tab << "lock (eventLock) {\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "lock (eventLock)\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "var wRef = new WeakReference(this);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Efl.EventCb callerCb = (IntPtr data, ref Efl.Event.NativeStruct evt) =>\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "var obj = wRef.Target as Efl.Eo.IWrapper;\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "if (obj != null)\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << event_args
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "try\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "value?.Invoke(obj, args);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "catch (Exception e)\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error(e.ToString());\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Error.Set(Eina.Error.UNHANDLED_EXCEPTION);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "};\n\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "string key = \"_" << upper_c_name << "\";\n" << scope_tab << scope_tab << scope_tab << scope_tab << "string key = \"_" << upper_c_name << "\";\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "if (AddNativeEventHandler(" << library_name << ", key, this.evt_" << event_name << "_delegate)) {\n" << scope_tab << scope_tab << scope_tab << scope_tab << "AddNativeEventHandler(" << library_name << ", key, callerCb, value);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "eventHandlers.AddHandler(" << event_name << "Key , value);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "} else\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Error adding proxy for event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << "}\n" // End of lock block << scope_tab << scope_tab << scope_tab << "}\n" // End of lock block
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << "remove {\n" << scope_tab << scope_tab << "remove\n"
<< scope_tab << scope_tab << scope_tab << "lock (eventLock) {\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "lock (eventLock)\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "string key = \"_" << upper_c_name << "\";\n" << scope_tab << scope_tab << scope_tab << scope_tab << "string key = \"_" << upper_c_name << "\";\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "if (RemoveNativeEventHandler(key, this.evt_" << event_name << "_delegate)) { \n" << scope_tab << scope_tab << scope_tab << scope_tab << "RemoveNativeEventHandler(" << library_name << ", key, value);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "eventHandlers.RemoveHandler(" << event_name << "Key , value);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "} else\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Error removing proxy for event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << "}\n" // End of lock block << scope_tab << scope_tab << scope_tab << "}\n" // End of lock block
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
@ -365,13 +456,6 @@ struct is_eager_generator<struct ::eolian_mono::event_declaration_generator> : s
template <> template <>
struct is_generator<struct ::eolian_mono::event_declaration_generator> : std::true_type {}; struct is_generator<struct ::eolian_mono::event_declaration_generator> : std::true_type {};
template <>
struct is_eager_generator<struct ::eolian_mono::event_registration_generator> : std::true_type {};
template <>
struct is_generator<struct ::eolian_mono::event_registration_generator> : std::true_type {};
template <>
struct is_generator<struct ::eolian_mono::event_registration_parameterized> : std::true_type {};
template <> template <>
struct is_eager_generator<struct ::eolian_mono::event_definition_generator> : std::true_type {}; struct is_eager_generator<struct ::eolian_mono::event_definition_generator> : std::true_type {};
template <> template <>
@ -385,10 +469,6 @@ struct attributes_needed<struct ::eolian_mono::event_argument_wrapper_generator>
template <> template <>
struct attributes_needed<struct ::eolian_mono::event_declaration_generator> : std::integral_constant<int, 1> {}; struct attributes_needed<struct ::eolian_mono::event_declaration_generator> : std::integral_constant<int, 1> {};
template <> template <>
struct attributes_needed<struct ::eolian_mono::event_registration_generator> : std::integral_constant<int, 1> {};
template <>
struct attributes_needed<struct ::eolian_mono::event_registration_parameterized> : std::integral_constant<int, 1> {};
template <>
struct attributes_needed<struct ::eolian_mono::event_definition_generator> : std::integral_constant<int, 1> {}; struct attributes_needed<struct ::eolian_mono::event_definition_generator> : std::integral_constant<int, 1> {};
template <> template <>
struct attributes_needed<struct ::eolian_mono::event_definition_parameterized> : std::integral_constant<int, 1> {}; struct attributes_needed<struct ::eolian_mono::event_definition_parameterized> : std::integral_constant<int, 1> {};

View File

@ -103,7 +103,7 @@ struct native_function_definition_generator
/****/ /****/
<< scope_tab << scope_tab << "Eina.Log.Debug(\"function " << string << " was called\");\n" << scope_tab << scope_tab << "Eina.Log.Debug(\"function " << string << " was called\");\n"
/****/ /****/
<< scope_tab << scope_tab << "Efl.Eo.IWrapper wrapper = Efl.Eo.Globals.data_get(pd);\n" << scope_tab << scope_tab << "Efl.Eo.IWrapper wrapper = Efl.Eo.Globals.PrivateDataGet(pd);\n"
<< scope_tab << scope_tab << "if(wrapper != null) {\n" << scope_tab << scope_tab << "if(wrapper != null) {\n"
<< scope_tab << scope_tab << scope_tab << eolian_mono::native_function_definition_preamble() << scope_tab << scope_tab << scope_tab << eolian_mono::native_function_definition_preamble()
<< scope_tab << scope_tab << scope_tab << "try {\n" << scope_tab << scope_tab << scope_tab << "try {\n"

View File

@ -56,7 +56,7 @@ struct function_pointer {
return false; return false;
// Wrapper type, with callback matching the Unamanaged one // Wrapper type, with callback matching the Unamanaged one
if (!as_generator("internal class " << f_name << "Wrapper\n" if (!as_generator("internal class " << f_name << "Wrapper : IDisposable\n"
<< "{\n\n" << "{\n\n"
<< scope_tab << "private " << f_name << "Internal _cb;\n" << scope_tab << "private " << f_name << "Internal _cb;\n"
<< scope_tab << "private IntPtr _cb_data;\n" << scope_tab << "private IntPtr _cb_data;\n"
@ -71,8 +71,31 @@ struct function_pointer {
<< scope_tab << "~" << f_name << "Wrapper()\n" << scope_tab << "~" << f_name << "Wrapper()\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "Dispose(false);\n"
<< scope_tab << "}\n\n"
<< scope_tab << "protected virtual void Dispose(bool disposing)\n"
<< scope_tab << "{\n"
<< scope_tab << scope_tab << "if (this._cb_free_cb != null)\n" << scope_tab << scope_tab << "if (this._cb_free_cb != null)\n"
<< scope_tab << scope_tab << scope_tab << "this._cb_free_cb(this._cb_data);\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "if (disposing)\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "this._cb_free_cb(this._cb_data);\n"
<< scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << "else\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(this._cb_free_cb, this._cb_data);\n"
<< scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << "this._cb_free_cb = null;\n"
<< scope_tab << scope_tab << scope_tab << "this._cb_data = IntPtr.Zero;\n"
<< scope_tab << scope_tab << scope_tab << "this._cb = null;\n"
<< scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n\n"
<< scope_tab << "public void Dispose()\n"
<< scope_tab << "{\n"
<< scope_tab << scope_tab << "Dispose(true);\n"
<< scope_tab << scope_tab << "GC.SuppressFinalize(this);\n"
<< scope_tab << "}\n\n" << scope_tab << "}\n\n"
<< scope_tab << "internal " << type << " ManagedCb(" << (parameter % ",") << ")\n" << scope_tab << "internal " << type << " ManagedCb(" << (parameter % ",") << ")\n"

View File

@ -44,7 +44,10 @@ struct function_registration_generator
return false; return false;
if(!as_generator if(!as_generator
(scope_tab << scope_tab << "descs.Add(new Efl_Op_Description() {" (scope_tab << scope_tab
<< "if (methods.FirstOrDefault(m => m.Name == \"" << string << "\") != null)\n"
<< scope_tab << scope_tab << scope_tab
<< "descs.Add(new Efl_Op_Description() {"
#ifdef _WIN32 #ifdef _WIN32
<< "api_func = Marshal.StringToHGlobalAnsi(\"" << string << "\")" << "api_func = Marshal.StringToHGlobalAnsi(\"" << string << "\")"
#else #else
@ -52,7 +55,7 @@ struct function_registration_generator
#endif #endif
<< ", func = Marshal.GetFunctionPointerForDelegate(" << string << "_static_delegate)});\n" << ", func = Marshal.GetFunctionPointerForDelegate(" << string << "_static_delegate)});\n"
) )
.generate(sink, std::make_tuple(f.c_name, f.c_name), context)) .generate(sink, std::make_tuple(name_helpers::managed_method_name(f), f.c_name, f.c_name), context))
return false; return false;
return true; return true;
} }

View File

@ -31,20 +31,6 @@
namespace eolian_mono { namespace eolian_mono {
template <typename OutputIterator, typename Context>
static bool generate_static_cast_method(OutputIterator sink, grammar::attributes::klass_def const& cls, Context const &context)
{
return as_generator(
scope_tab << "///<summary>Casts obj into an instance of this type.</summary>\n"
<< scope_tab << "public " << (helpers::has_regular_ancestor(cls) ? "new " : "") <<"static " << name_helpers::klass_concrete_name(cls) << " static_cast(Efl.Object obj)\n"
<< scope_tab << "{\n"
<< scope_tab << scope_tab << "if (obj == null)\n"
<< scope_tab << scope_tab << scope_tab << "throw new System.ArgumentNullException(\"obj\");\n"
<< scope_tab << scope_tab << "return new " << name_helpers::klass_concrete_name(cls) << "(obj.NativeHandle);\n"
<< scope_tab << "}\n"
).generate(sink, nullptr, context);
}
template <typename OutputIterator, typename Context> template <typename OutputIterator, typename Context>
static bool generate_equals_method(OutputIterator sink, Context const &context) static bool generate_equals_method(OutputIterator sink, Context const &context)
{ {
@ -110,7 +96,7 @@ struct klass
suffix = "CLASS"; suffix = "CLASS";
break; break;
case attributes::class_type::abstract_: case attributes::class_type::abstract_:
class_type = "class"; class_type = "abstract class";
suffix = "CLASS"; suffix = "CLASS";
break; break;
case attributes::class_type::mixin: case attributes::class_type::mixin:
@ -207,7 +193,7 @@ struct klass
}); });
// Concrete class for interfaces, mixins, etc. // Concrete class for interfaces, mixins, etc.
if(class_type != "class") if(class_type != "class" && class_type != "abstract class")
{ {
auto concrete_cxt = context_add_tag(class_context{class_context::concrete}, context); auto concrete_cxt = context_add_tag(class_context{class_context::concrete}, context);
auto concrete_name = name_helpers::klass_concrete_name(cls); auto concrete_name = name_helpers::klass_concrete_name(cls);
@ -234,10 +220,9 @@ struct klass
<< ")] internal static extern System.IntPtr\n" << ")] internal static extern System.IntPtr\n"
<< scope_tab << scope_tab << name_helpers::klass_get_name(cls) << "();\n" << scope_tab << scope_tab << name_helpers::klass_get_name(cls) << "();\n"
<< scope_tab << "///<summary>Internal usage: Constructs an instance from a native pointer. This is used when interacting with C code and should not be used directly.</summary>\n" << scope_tab << "///<summary>Internal usage: Constructs an instance from a native pointer. This is used when interacting with C code and should not be used directly.</summary>\n"
<< scope_tab << "public " << concrete_name << "(System.IntPtr raw)" << (root ? "" : " : base(raw)") << "\n" << scope_tab << "private " << concrete_name << "(System.IntPtr raw)" << (root ? "" : " : base(raw)") << "\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << (root ? "handle = raw;\n" : "") << scope_tab << scope_tab << (root ? "handle = raw;\n" : "")
<< scope_tab << scope_tab << "RegisterEventProxies();\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
) )
.generate(sink, attributes::unused, concrete_cxt)) .generate(sink, attributes::unused, concrete_cxt))
@ -246,18 +231,12 @@ struct klass
if (!generate_dispose_methods(sink, cls, concrete_cxt)) if (!generate_dispose_methods(sink, cls, concrete_cxt))
return false; return false;
if (!generate_static_cast_method(sink, cls, concrete_cxt))
return false;
if (!generate_equals_method(sink, concrete_cxt)) if (!generate_equals_method(sink, concrete_cxt))
return false; return false;
if (!generate_events(sink, cls, concrete_cxt)) if (!generate_events(sink, cls, concrete_cxt))
return false; return false;
if (!generate_events_registration(sink, cls, concrete_cxt))
return false;
// Parts // Parts
if(!as_generator(*(part_definition)) if(!as_generator(*(part_definition))
.generate(sink, cls.parts, concrete_cxt)) return false; .generate(sink, cls.parts, concrete_cxt)) return false;
@ -296,7 +275,7 @@ struct klass
} }
// Inheritable class // Inheritable class
if(class_type == "class") if(class_type == "class" || class_type == "abstract class")
{ {
auto inherit_cxt = context_add_tag(class_context{class_context::inherit}, context); auto inherit_cxt = context_add_tag(class_context{class_context::inherit}, context);
@ -327,18 +306,12 @@ struct klass
if (!generate_dispose_methods(sink, cls, inherit_cxt)) if (!generate_dispose_methods(sink, cls, inherit_cxt))
return false; return false;
if (!generate_static_cast_method(sink, cls, inherit_cxt))
return false;
if (!generate_equals_method(sink, inherit_cxt)) if (!generate_equals_method(sink, inherit_cxt))
return false; return false;
if (!generate_events(sink, cls, inherit_cxt)) if (!generate_events(sink, cls, inherit_cxt))
return false; return false;
if (!generate_events_registration(sink, cls, inherit_cxt))
return false;
// Parts // Parts
if(!as_generator(*(part_definition)) if(!as_generator(*(part_definition))
.generate(sink, cls.parts, inherit_cxt)) return false; .generate(sink, cls.parts, inherit_cxt)) return false;
@ -396,6 +369,7 @@ struct klass
<< scope_tab << "public override System.Collections.Generic.List<Efl_Op_Description> GetEoOps(System.Type type)\n" << scope_tab << "public override System.Collections.Generic.List<Efl_Op_Description> GetEoOps(System.Type type)\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "var descs = new System.Collections.Generic.List<Efl_Op_Description>();\n" << scope_tab << scope_tab << "var descs = new System.Collections.Generic.List<Efl_Op_Description>();\n"
<< scope_tab << scope_tab << "var methods = Efl.Eo.Globals.GetUserMethods(type);\n"
) )
.generate(sink, attributes::unused, inative_cxt)) .generate(sink, attributes::unused, inative_cxt))
return false; return false;
@ -479,7 +453,9 @@ struct klass
return true; return true;
if (cls.get_all_events().size() > 0) if (cls.get_all_events().size() > 0)
if (!as_generator(scope_tab << (is_inherit ? "protected " : "private ") << "EventHandlerList eventHandlers = new EventHandlerList();\n").generate(sink, attributes::unused, context)) if (!as_generator(scope_tab << visibility << "Dictionary<(IntPtr desc, object evtDelegate), (IntPtr evtCallerPtr, Efl.EventCb evtCaller)> eoEvents = new Dictionary<(IntPtr desc, object evtDelegate), (IntPtr evtCallerPtr, Efl.EventCb evtCaller)>();\n"
<< scope_tab << visibility << "readonly object eventLock = new object();\n")
.generate(sink, attributes::unused, context))
return false; return false;
if (is_inherit) if (is_inherit)
@ -534,14 +510,30 @@ struct klass
<< scope_tab << scope_tab << "FinishInstantiation();\n" << scope_tab << scope_tab << "FinishInstantiation();\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
<< scope_tab << "///<summary>Internal usage: Constructs an instance from a native pointer. This is used when interacting with C code and should not be used directly.</summary>\n" << scope_tab << "///<summary>Internal usage: Constructs an instance from a native pointer. This is used when interacting with C code and should not be used directly.</summary>\n"
<< scope_tab << "public " << inherit_name << "(System.IntPtr raw)" << (root ? "" : " : base(raw)") << "\n" << scope_tab << "protected " << inherit_name << "(System.IntPtr raw)" << (root ? "" : " : base(raw)") << "\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << (root ? "handle = raw;\n" : "") << scope_tab << scope_tab << (root ? "handle = raw;\n" : "")
<< scope_tab << scope_tab << "RegisterEventProxies();\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
).generate(sink, std::make_tuple(constructors, constructors, constructors), context)) ).generate(sink, std::make_tuple(constructors, constructors, constructors), context))
return false; return false;
// Some abstract classes (like Efl.App) have a simple regular class that is used to instantiate them
// in a controlled manner. These fake-private classes can be returned from C and we use a similarly-named
// private class to be able to instantiate them when they get to the C# world.
if (cls.type == attributes::class_type::abstract_)
{
if (!as_generator(
scope_tab << "[Efl.Eo.PrivateNativeClass]\n"
<< scope_tab << "private class " << inherit_name << "Realized : " << inherit_name << "\n"
<< scope_tab << "{\n"
<< scope_tab << scope_tab << "private " << inherit_name << "Realized(IntPtr ptr) : base(ptr)\n"
<< scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n"
).generate(sink, attributes::unused, context))
return false;
}
// Internal constructors // Internal constructors
if (!root) if (!root)
{ {
@ -563,14 +555,14 @@ struct klass
<< scope_tab << scope_tab << scope_tab << "actual_klass = Efl.Eo.ClassRegister.GetInheritKlassOrRegister(base_klass, ((object)this).GetType());\n" << scope_tab << scope_tab << scope_tab << "actual_klass = Efl.Eo.ClassRegister.GetInheritKlassOrRegister(base_klass, ((object)this).GetType());\n"
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << "handle = Efl.Eo.Globals.instantiate_start(actual_klass, parent);\n" << scope_tab << scope_tab << "handle = Efl.Eo.Globals.instantiate_start(actual_klass, parent);\n"
<< scope_tab << scope_tab << "RegisterEventProxies();\n" << scope_tab << scope_tab << "if (inherited)\n"
<< scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.PrivateDataSet(this);\n"
<< scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
<< scope_tab << "protected void FinishInstantiation()\n" << scope_tab << "protected void FinishInstantiation()\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "if (inherited) {\n"
<< scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.data_set(this);\n"
<< scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << "handle = Efl.Eo.Globals.instantiate_end(handle);\n" << scope_tab << scope_tab << "handle = Efl.Eo.Globals.instantiate_end(handle);\n"
<< scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n" << scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
@ -582,7 +574,6 @@ struct klass
template <typename OutputIterator, typename Context> template <typename OutputIterator, typename Context>
bool generate_dispose_methods(OutputIterator sink, attributes::klass_def const& cls, Context const& context) const bool generate_dispose_methods(OutputIterator sink, attributes::klass_def const& cls, Context const& context) const
{ {
std::string name = join_namespaces(cls.namespaces, '.') + cls.eolian_name;
if (helpers::has_regular_ancestor(cls)) if (helpers::has_regular_ancestor(cls))
return true; return true;
@ -590,85 +581,64 @@ struct klass
auto inherit_name = name_helpers::klass_concrete_name(cls); auto inherit_name = name_helpers::klass_concrete_name(cls);
std::string events_gchandle;
if (cls.get_all_events().size() > 0)
{
auto events_gchandle_sink = std::back_inserter(events_gchandle);
if (!as_generator(scope_tab << scope_tab << scope_tab << "if (eoEvents.Count != 0)\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "GCHandle gcHandle = GCHandle.Alloc(eoEvents);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "gcHandlePtr = GCHandle.ToIntPtr(gcHandle);\n"
<< scope_tab << scope_tab << scope_tab << "}\n\n")
.generate(events_gchandle_sink, attributes::unused, context))
return false;
}
return as_generator( return as_generator(
scope_tab << "///<summary>Destructor.</summary>\n" scope_tab << "///<summary>Destructor.</summary>\n"
<< scope_tab << "~" << inherit_name << "()\n" << scope_tab << "~" << inherit_name << "()\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "Dispose(false);\n" << scope_tab << scope_tab << "Dispose(false);\n"
<< scope_tab << "}\n" << scope_tab << "}\n\n"
<< scope_tab << "///<summary>Releases the underlying native instance.</summary>\n" << scope_tab << "///<summary>Releases the underlying native instance.</summary>\n"
<< scope_tab << visibility << "void Dispose(bool disposing)\n" << scope_tab << visibility << "void Dispose(bool disposing)\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "if (handle != System.IntPtr.Zero) {\n" << scope_tab << scope_tab << "if (handle != System.IntPtr.Zero)\n"
<< scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.efl_unref(handle);\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "handle = System.IntPtr.Zero;\n" << scope_tab << scope_tab << scope_tab << "IntPtr h = handle;\n"
<< scope_tab << scope_tab << scope_tab << "handle = IntPtr.Zero;\n\n"
<< scope_tab << scope_tab << scope_tab << "IntPtr gcHandlePtr = IntPtr.Zero;\n"
<< events_gchandle
<< scope_tab << scope_tab << scope_tab << "if (disposing)\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.efl_mono_native_dispose(h, gcHandlePtr);\n"
<< scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << "else\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Monitor.Enter(Efl.Eo.Config.InitLock);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "if (Efl.Eo.Config.Initialized)\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << scope_tab << "Efl.Eo.Globals.efl_mono_thread_safe_native_dispose(h, gcHandlePtr);\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Monitor.Exit(Efl.Eo.Config.InitLock);\n"
<< scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n" << scope_tab << "}\n\n"
<< scope_tab << "///<summary>Releases the underlying native instance.</summary>\n" << scope_tab << "///<summary>Releases the underlying native instance.</summary>\n"
<< scope_tab << "public void Dispose()\n" << scope_tab << "public void Dispose()\n"
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "Dispose(true);\n" << scope_tab << scope_tab << "Dispose(true);\n"
<< scope_tab << scope_tab << "GC.SuppressFinalize(this);\n" << scope_tab << scope_tab << "GC.SuppressFinalize(this);\n"
<< scope_tab << "}\n" << scope_tab << "}\n\n"
).generate(sink, attributes::unused, context); ).generate(sink, attributes::unused, context);
} }
template <typename OutputIterator, typename Context>
bool generate_events_registration(OutputIterator sink, attributes::klass_def const& cls, Context const& context) const
{
bool root = !helpers::has_regular_ancestor(cls);
std::string virtual_modifier = " ";
if (!root)
virtual_modifier = "override ";
else
{
if (is_inherit_context(context))
virtual_modifier = "virtual ";
}
// Event proxy registration
if (!as_generator(
scope_tab << "///<summary>Register the Eo event wrappers making the bridge to C# events. Internal usage only.</summary>\n"
<< scope_tab << (is_inherit_context(context) || !root ? "protected " : "") << virtual_modifier << "void RegisterEventProxies()\n"
<< scope_tab << "{\n"
)
.generate(sink, NULL, context))
return false;
// Generate event registrations here
if (!root)
if (!as_generator(scope_tab << scope_tab << "base.RegisterEventProxies();\n").generate(sink, NULL, context))
return false;
// Assigning the delegates
if (!as_generator(*(event_registration(cls, cls))).generate(sink, cls.events, context))
return false;
for (auto&& c : helpers::non_implemented_interfaces(cls, context))
{
// Only non-regular types (which declare events through interfaces) need to register them.
if (c.type == attributes::class_type::regular)
continue;
attributes::klass_def klass(get_klass(c, cls.unit), cls.unit);
if (!as_generator(*(event_registration(klass, cls))).generate(sink, klass.events, context))
return false;
}
if (!as_generator(
scope_tab << "}\n"
).generate(sink, NULL, context))
return false;
return true;
}
template <typename OutputIterator, typename Context> template <typename OutputIterator, typename Context>
bool generate_events(OutputIterator sink, attributes::klass_def const& cls, Context const& context) const bool generate_events(OutputIterator sink, attributes::klass_def const& cls, Context const& context) const
{ {
@ -680,69 +650,70 @@ struct klass
if (!helpers::has_regular_ancestor(cls)) if (!helpers::has_regular_ancestor(cls))
{ {
if (!as_generator(scope_tab << visibility << "readonly object eventLock = new object();\n"
<< scope_tab << visibility << "Dictionary<string, int> event_cb_count = new Dictionary<string, int>();\n")
.generate(sink, NULL, context))
return false;
// Callback registration functions // Callback registration functions
if (!as_generator( if (!as_generator(
scope_tab << "///<summary>Adds a new event handler, registering it to the native event. For internal use only.</summary>\n" scope_tab << "///<summary>Adds a new event handler, registering it to the native event. For internal use only.</summary>\n"
<< scope_tab << "///<param name=\"lib\">The name of the native library definining the event.</param>\n" << scope_tab << "///<param name=\"lib\">The name of the native library definining the event.</param>\n"
<< scope_tab << "///<param name=\"key\">The name of the native event.</param>\n" << scope_tab << "///<param name=\"key\">The name of the native event.</param>\n"
<< scope_tab << "///<param name=\"evt_delegate\">The delegate to be called on event raising.</param>\n" << scope_tab << "///<param name=\"evtCaller\">Delegate to be called by native code on event raising.</param>\n"
<< scope_tab << "///<returns>True if the delegate was successfully registered.</returns>\n" << scope_tab << "///<param name=\"evtDelegate\">Managed delegate that will be called by evtCaller on event raising.</param>\n"
<< scope_tab << visibility << "bool AddNativeEventHandler(string lib, string key, Efl.EventCb evt_delegate) {\n" << scope_tab << visibility << "void AddNativeEventHandler(string lib, string key, Efl.EventCb evtCaller, object evtDelegate)\n"
<< scope_tab << scope_tab << "int event_count = 0;\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "if (!event_cb_count.TryGetValue(key, out event_count))\n"
<< scope_tab << scope_tab << scope_tab << "event_cb_count[key] = event_count;\n"
<< scope_tab << scope_tab << "if (event_count == 0) {\n"
<< scope_tab << scope_tab << scope_tab << "IntPtr desc = Efl.EventDescription.GetNative(lib, key);\n" << scope_tab << scope_tab << "IntPtr desc = Efl.EventDescription.GetNative(lib, key);\n"
<< scope_tab << scope_tab << scope_tab << "if (desc == IntPtr.Zero) {\n" << scope_tab << scope_tab << "if (desc == IntPtr.Zero)\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to get native event {key}\");\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "return false;\n" << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to get native event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << "if (eoEvents.ContainsKey((desc, evtDelegate)))\n"
<< scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Log.Warning($\"Event proxy for event {key} already registered!\");\n"
<< scope_tab << scope_tab << scope_tab << "return;\n"
<< scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << "IntPtr evtCallerPtr = Marshal.GetFunctionPointerForDelegate(evtCaller);\n"
<< scope_tab << scope_tab << "if (!Efl.Eo.Globals.efl_event_callback_priority_add(handle, desc, 0, evtCallerPtr, IntPtr.Zero))\n"
<< scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to add event proxy for event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << "return;\n"
<< scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << "eoEvents[(desc, evtDelegate)] = (evtCallerPtr, evtCaller);\n"
<< scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n"
<< scope_tab << "}\n\n"
<< scope_tab << scope_tab << scope_tab << " bool result = Efl.Eo.Globals.efl_event_callback_priority_add(handle, desc, 0, evt_delegate, System.IntPtr.Zero);\n"
<< scope_tab << scope_tab << scope_tab << "if (!result) {\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to add event proxy for event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "return false;\n"
<< scope_tab << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n"
<< scope_tab << scope_tab << "} \n"
<< scope_tab << scope_tab << "event_cb_count[key]++;\n"
<< scope_tab << scope_tab << "return true;\n"
<< scope_tab << "}\n"
<< scope_tab << "///<summary>Removes the given event handler for the given event. For internal use only.</summary>\n" << scope_tab << "///<summary>Removes the given event handler for the given event. For internal use only.</summary>\n"
<< scope_tab << "///<param name=\"lib\">The name of the native library definining the event.</param>\n"
<< scope_tab << "///<param name=\"key\">The name of the native event.</param>\n" << scope_tab << "///<param name=\"key\">The name of the native event.</param>\n"
<< scope_tab << "///<param name=\"evt_delegate\">The delegate to be removed.</param>\n" << scope_tab << "///<param name=\"evtDelegate\">The delegate to be removed.</param>\n"
<< scope_tab << "///<returns>True if the delegate was successfully registered.</returns>\n" << scope_tab << visibility << "void RemoveNativeEventHandler(string lib, string key, object evtDelegate)\n"
<< scope_tab << visibility << "bool RemoveNativeEventHandler(string key, Efl.EventCb evt_delegate) {\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "int event_count = 0;\n"
<< scope_tab << scope_tab << "if (!event_cb_count.TryGetValue(key, out event_count))\n"
<< scope_tab << scope_tab << scope_tab << "event_cb_count[key] = event_count;\n"
<< scope_tab << scope_tab << "if (event_count == 1) {\n"
<< scope_tab << scope_tab << scope_tab << "IntPtr desc = Efl.EventDescription.GetNative(" << scope_tab << scope_tab << "IntPtr desc = Efl.EventDescription.GetNative(lib, key);\n"
<< context_find_tag<library_context>(context).actual_library_name(cls.filename) << ", key);\n" << scope_tab << scope_tab << "if (desc == IntPtr.Zero)\n"
<< scope_tab << scope_tab << scope_tab << "if (desc == IntPtr.Zero) {\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to get native event {key}\");\n" << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to get native event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "return false;\n" << scope_tab << scope_tab << scope_tab << "return;\n"
<< scope_tab << scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << scope_tab << "bool result = Efl.Eo.Globals.efl_event_callback_del(handle, desc, evt_delegate, System.IntPtr.Zero);\n" << scope_tab << scope_tab << "var evtPair = (desc, evtDelegate);\n"
<< scope_tab << scope_tab << scope_tab << "if (!result) {\n" << scope_tab << scope_tab << "if (eoEvents.TryGetValue(evtPair, out var caller))\n"
<< scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "if (!Efl.Eo.Globals.efl_event_callback_del(handle, desc, caller.evtCallerPtr, IntPtr.Zero))\n"
<< scope_tab << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to remove event proxy for event {key}\");\n" << scope_tab << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Failed to remove event proxy for event {key}\");\n"
<< scope_tab << scope_tab << scope_tab << scope_tab << "return false;\n" << scope_tab << scope_tab << scope_tab << scope_tab << "return;\n"
<< scope_tab << scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << scope_tab << "}\n\n"
<< scope_tab << scope_tab << scope_tab << "eoEvents.Remove(evtPair);\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n" << scope_tab << scope_tab << scope_tab << "Eina.Error.RaiseIfUnhandledException();\n"
<< scope_tab << scope_tab << "} else if (event_count == 0) {\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Trying to remove proxy for event {key} when there is nothing registered.\");\n" << scope_tab << scope_tab << "else\n"
<< scope_tab << scope_tab << scope_tab << "return false;\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << "} \n" << scope_tab << scope_tab << scope_tab << "Eina.Log.Error($\"Trying to remove proxy for event {key} when it is nothing registered.\");\n"
<< scope_tab << scope_tab << "event_cb_count[key]--;\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << scope_tab << "return true;\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
) )
.generate(sink, NULL, context)) .generate(sink, NULL, context))

View File

@ -27,8 +27,7 @@ struct part_definition_generator
<< scope_tab << "{\n" << scope_tab << "{\n"
<< scope_tab << scope_tab << "get\n" << scope_tab << scope_tab << "get\n"
<< scope_tab << scope_tab << "{\n" << scope_tab << scope_tab << "{\n"
<< scope_tab << scope_tab << scope_tab << "Efl.Object obj = Efl.IPartNativeInherit.efl_part_get_ptr.Value.Delegate(NativeHandle, \"" << part.name << "\");\n" << scope_tab << scope_tab << scope_tab << "return Efl.IPartNativeInherit.efl_part_get_ptr.Value.Delegate(NativeHandle, \"" << part.name << "\") as " << part_klass_name << ";\n"
<< scope_tab << scope_tab << scope_tab << "return " << part_klass_name << ".static_cast(obj);\n"
<< scope_tab << scope_tab << "}\n" << scope_tab << scope_tab << "}\n"
<< scope_tab << "}\n" << scope_tab << "}\n"
).generate(sink, part.documentation, context); ).generate(sink, part.documentation, context);

View File

@ -48,7 +48,7 @@ struct to_internal_field_convert_generator
if (klass) if (klass)
{ {
if (!as_generator( if (!as_generator(
indent << scope_tab << scope_tab << "_internal_struct." << string << " = _external_struct." << string << ".NativeHandle;\n") indent << scope_tab << scope_tab << "_internal_struct." << string << " = _external_struct." << string << "?.NativeHandle ?? System.IntPtr.Zero;\n")
.generate(sink, std::make_tuple(field_name, field_name), context)) .generate(sink, std::make_tuple(field_name, field_name), context))
return false; return false;
} }
@ -112,7 +112,7 @@ struct to_internal_field_convert_generator
else if (field.type.c_type == "Eina_Value *" || field.type.c_type == "const Eina_Value *") else if (field.type.c_type == "Eina_Value *" || field.type.c_type == "const Eina_Value *")
{ {
if (!as_generator( if (!as_generator(
indent << scope_tab << scope_tab << "_internal_struct." << string << " = _external_struct." << string << ".NativeHandle;\n" indent << scope_tab << scope_tab << "_internal_struct." << string << " = _external_struct." << string << "?.NativeHandle ?? System.IntPtr.Zero;\n"
).generate(sink, std::make_tuple(field_name, field_name), context)) ).generate(sink, std::make_tuple(field_name, field_name), context))
return false; return false;
} }
@ -159,10 +159,8 @@ struct to_external_field_convert_generator
if (!as_generator( if (!as_generator(
"\n" "\n"
<< indent << scope_tab << scope_tab << "_external_struct." << string << indent << scope_tab << scope_tab << "_external_struct." << string
<< " = (" << concrete_name << ") System.Activator.CreateInstance(typeof(" << " = (" << concrete_name << ") Efl.Eo.Globals.CreateWrapperFor(_internal_struct." << string << ");\n"
<< concrete_name << "), new System.Object[] {_internal_struct." << string << "});\n" ).generate(sink, std::make_tuple(field_name, field_name), context))
<< indent << scope_tab << scope_tab << "Efl.Eo.Globals.efl_ref(_internal_struct." << string << ");\n")
.generate(sink, std::make_tuple(field_name, field_name, field_name), context))
return false; return false;
} }
else if (field.type.c_type == "Eina_Binbuf *" || field.type.c_type == "const Eina_Binbuf *") else if (field.type.c_type == "Eina_Binbuf *" || field.type.c_type == "const Eina_Binbuf *")

View File

@ -134,6 +134,7 @@ run(options_type const& opts)
"using System.Runtime.InteropServices;\n" "using System.Runtime.InteropServices;\n"
"using System.Collections.Generic;\n" "using System.Collections.Generic;\n"
"using System.Linq;\n" "using System.Linq;\n"
"using System.Threading;\n"
"using System.ComponentModel;\n") "using System.ComponentModel;\n")
.generate(iterator, efl::eolian::grammar::attributes::unused, efl::eolian::grammar::context_null())) .generate(iterator, efl::eolian::grammar::attributes::unused, efl::eolian::grammar::context_null()))
{ {
@ -288,8 +289,8 @@ _usage(const char *progname)
<< " -c, --class <name> The Eo class name to generate code for." << std::endl << " -c, --class <name> The Eo class name to generate code for." << std::endl
<< " -D, --out-dir <dir> Output directory where generated code will be written." << std::endl << " -D, --out-dir <dir> Output directory where generated code will be written." << std::endl
<< " -I, --in <file/dir> The source containing the .eo descriptions." << std::endl << " -I, --in <file/dir> The source containing the .eo descriptions." << std::endl
<< " -o, --out-file <file> The output file name. [default: <classname>.eo.hh]" << std::endl << " -o, --out-file <file> The output file name. [default: <classname>.eo.cs]" << std::endl
<< " -n, --namespace <ns> Wrap generated code in a namespace. [Eg: efl::ecore::file]" << std::endl << " -n, --namespace <ns> Wrap generated code in a namespace. [Eg: Efl.Ui.Widget]" << std::endl
<< " -r, --recurse Recurse input directories loading .eo files." << std::endl << " -r, --recurse Recurse input directories loading .eo files." << std::endl
<< " -v, --version Print the version." << std::endl << " -v, --version Print the version." << std::endl
<< " -b, --beta Enable @beta methods." << std::endl << " -b, --beta Enable @beta methods." << std::endl

View File

@ -6,10 +6,11 @@ using System.Threading;
using static Efl.UnsafeNativeMethods; using static Efl.UnsafeNativeMethods;
namespace Efl { namespace Efl
{
static class UnsafeNativeMethods {
static class UnsafeNativeMethods
{
private delegate void init_func_delegate(); private delegate void init_func_delegate();
[DllImport(efl.Libs.Ecore)] public static extern void ecore_init(); [DllImport(efl.Libs.Ecore)] public static extern void ecore_init();
[DllImport(efl.Libs.Ecore)] public static extern void ecore_shutdown(); [DllImport(efl.Libs.Ecore)] public static extern void ecore_shutdown();
@ -27,39 +28,48 @@ static class UnsafeNativeMethods {
[DllImport(efl.Libs.Elementary)] public static extern void elm_run(); [DllImport(efl.Libs.Elementary)] public static extern void elm_run();
[DllImport(efl.Libs.Elementary)] public static extern void elm_exit(); [DllImport(efl.Libs.Elementary)] public static extern void elm_exit();
static UnsafeNativeMethods() { static UnsafeNativeMethods()
{
_evas_init = new Efl.Eo.FunctionWrapper<init_func_delegate>("evas", "evas_init"); _evas_init = new Efl.Eo.FunctionWrapper<init_func_delegate>("evas", "evas_init");
} }
public static void evas_init() public static void evas_init()
{ {
_evas_init.Value.Delegate(); _evas_init.Value.Delegate();
} }
} }
public static class All { public static class All
{
private static bool InitializedUi = false; private static bool InitializedUi = false;
public static void Init(Efl.Csharp.Components components=Efl.Csharp.Components.Basic) { public static void Init(Efl.Csharp.Components components = Efl.Csharp.Components.Basic)
{
Eina.Config.Init(); Eina.Config.Init();
Efl.Eo.Config.Init(); Efl.Eo.Config.Init();
ecore_init(); ecore_init();
evas_init(); evas_init();
eldbus.Config.Init(); eldbus.Config.Init();
if (components == Efl.Csharp.Components.Ui) { if (components == Efl.Csharp.Components.Ui)
{
Efl.Ui.Config.Init(); Efl.Ui.Config.Init();
InitializedUi = true; InitializedUi = true;
} }
} }
/// <summary>Shutdowns all EFL subsystems.</summary> /// <summary>Shutdowns all EFL subsystems.</summary>
public static void Shutdown() { public static void Shutdown()
{
// Try to cleanup everything before actually shutting down. // Try to cleanup everything before actually shutting down.
System.GC.Collect(); System.GC.Collect();
System.GC.WaitForPendingFinalizers(); System.GC.WaitForPendingFinalizers();
if (InitializedUi) if (InitializedUi)
{
Efl.Ui.Config.Shutdown(); Efl.Ui.Config.Shutdown();
}
eldbus.Config.Shutdown(); eldbus.Config.Shutdown();
evas_shutdown(); evas_shutdown();
ecore_shutdown(); ecore_shutdown();
@ -69,29 +79,38 @@ public static class All {
} }
// Placeholder. Will move to elm_config.cs later // Placeholder. Will move to elm_config.cs later
namespace Ui { namespace Ui
{
public static class Config { public static class Config
public static void Init() { {
public static void Init()
{
// TODO Support elm command line arguments // TODO Support elm command line arguments
#if WIN32 // Not a native define, we define it in our build system #if WIN32 // Not a native define, we define it in our build system
// Ecore_Win32 uses OleInitialize, which requires single thread apartments // Ecore_Win32 uses OleInitialize, which requires single thread apartments
if (System.Threading.Thread.CurrentThread.GetApartmentState() != ApartmentState.STA) if (System.Threading.Thread.CurrentThread.GetApartmentState() != ApartmentState.STA)
{
throw new InvalidOperationException("UI Applications require STAThreadAttribute in Main()"); throw new InvalidOperationException("UI Applications require STAThreadAttribute in Main()");
}
#endif #endif
elm_init(0, IntPtr.Zero); elm_init(0, IntPtr.Zero);
elm_policy_set((int)Elm.Policy.Quit, (int)Elm.PolicyQuit.LastWindowHidden); elm_policy_set((int)Elm.Policy.Quit, (int)Elm.PolicyQuit.LastWindowHidden);
} }
public static void Shutdown() {
public static void Shutdown()
{
elm_shutdown(); elm_shutdown();
} }
public static void Run() { public static void Run()
{
elm_run(); elm_run();
} }
public static void Exit() { public static void Exit()
{
elm_exit(); elm_exit();
} }
} }

View File

@ -3,99 +3,131 @@ using System.Runtime.InteropServices;
using System.Threading; using System.Threading;
using static Efl.UnsafeNativeMethods; using static Efl.UnsafeNativeMethods;
namespace Efl { namespace Efl
namespace Csharp { {
///<summary>The components to be initialized.</summary>
public enum Components { namespace Csharp
///<summary>Basic components: Eina, Eo, Ecore, Evas and DBus.</summary> {
Basic,
///<summary>The same components of <see cref="Efl.Csharp.Components.Basic"/> and the Elementary widget toolkit.</summary> ///<summary>The components to be initialized.</summary>
Ui, public enum Components
} {
/// <summary> ///<summary>Basic components: Eina, Eo, Ecore, Evas and DBus.</summary>
/// This represents the entry point for the EFL framework Basic,
/// You can use this class to implement the 4 abstract methods which will then be called accordingly ///<summary>The same components of <see cref="Efl.Csharp.Components.Basic"/> and the Elementary widget toolkit.</summary>
/// All subsystems of efl are booted up correctly when the abstract methods of this class are called. Ui,
/// </summary> }
/// <remarks>
/// Calls to efl outside those efl-callbacks or outside the mainloop are not allowed and will lead to issues /// <summary>
/// </remarks> /// This represents the entry point for the EFL framework
/// <example> /// You can use this class to implement the 4 abstract methods which will then be called accordingly
/// UserApp is the class that implements the Application abstract /// All subsystems of efl are booted up correctly when the abstract methods of this class are called.
/// <code> /// </summary>
/// public static void Main() { /// <remarks>
/// UserApp editor = new UserApp(); /// Calls to efl outside those efl-callbacks or outside the mainloop are not allowed and will lead to issues
/// editor.Launch(editor); /// </remarks>
/// } /// <example>
/// </code> /// UserApp is the class that implements the Application abstract
/// </example> /// <code>
public abstract class Application { /// public static void Main()
//the initializied components /// {
private static Components initComponent; /// UserApp editor = new UserApp();
//what follows are 3 private functions to boot up the internals of efl /// editor.Launch(editor);
private static void Init(Efl.Csharp.Components component) { /// }
/// </code>
/// </example>
public abstract class Application
{
//the initializied components
private static Components initComponent;
//what follows are 3 private functions to boot up the internals of efl
private static void Init(Efl.Csharp.Components component)
{
Eina.Config.Init(); Eina.Config.Init();
Efl.Eo.Config.Init(); Efl.Eo.Config.Init();
ecore_init(); ecore_init();
evas_init(); evas_init();
eldbus.Config.Init(); eldbus.Config.Init();
if (component == Components.Ui) { if (component == Components.Ui)
// TODO Support elm command line arguments {
#if WIN32 // Not a native define, we define it in our build system // TODO Support elm command line arguments
// Ecore_Win32 uses OleInitialize, which requires single thread apartments #if WIN32 // Not a native define, we define it in our build system
if (System.Threading.Thread.CurrentThread.GetApartmentState() != ApartmentState.STA) // Ecore_Win32 uses OleInitialize, which requires single thread apartments
throw new InvalidOperationException("UI Applications require STAThreadAttribute in Main()"); if (System.Threading.Thread.CurrentThread.GetApartmentState() != ApartmentState.STA)
{
throw new InvalidOperationException("UI Applications require STAThreadAttribute in Main()");
}
#endif #endif
elm_init(0, IntPtr.Zero); elm_init(0, IntPtr.Zero);
elm_policy_set((int)Elm.Policy.Quit, (int)Elm.PolicyQuit.LastWindowHidden); elm_policy_set((int)Elm.Policy.Quit, (int)Elm.PolicyQuit.LastWindowHidden);
} }
initComponent = component; initComponent = component;
} }
private static void Shutdown() {
private static void Shutdown()
{
// Try to cleanup everything before actually shutting down. // Try to cleanup everything before actually shutting down.
System.GC.Collect(); System.GC.Collect();
System.GC.WaitForPendingFinalizers(); System.GC.WaitForPendingFinalizers();
if (initComponent == Components.Ui) { if (initComponent == Components.Ui)
elm_shutdown(); {
elm_shutdown();
} }
eldbus.Config.Shutdown(); eldbus.Config.Shutdown();
evas_shutdown(); evas_shutdown();
ecore_shutdown(); ecore_shutdown();
Efl.Eo.Config.Shutdown(); Efl.Eo.Config.Shutdown();
Eina.Config.Shutdown(); Eina.Config.Shutdown();
} }
/// <summary>
/// Called when the application is started. Arguments from the command line are passed here. /// <summary>
/// </summary> /// Called when the application is started. Arguments from the command line are passed here.
protected abstract void OnInitialize(Eina.Array<System.String> args); /// </summary>
/// <summary> protected abstract void OnInitialize(Eina.Array<System.String> args);
/// Arguments are passed here, Additional calls to this function may occure,
/// but then the initialization flag is set to false. /// <summary>
/// </summary> /// Arguments are passed here, Additional calls to this function may occure,
/// <remarks> /// but then the initialization flag is set to false.
/// When Initialize is true then OnInitialize is also called /// </summary>
/// </remarks> /// <remarks>
protected virtual void OnArguments(Efl.LoopArguments args) { } /// When Initialize is true then OnInitialize is also called
/// <summary> /// </remarks>
/// Called when the application is not going to be displayed, or is not used by a user for some time. protected virtual void OnArguments(Efl.LoopArguments args)
/// </summary> {
protected virtual void OnPause() { } }
/// <summary>
/// Called before an application is used again after a call to OnPause(). /// <summary>
/// </summary> /// Called when the application is not going to be displayed, or is not used by a user for some time.
protected virtual void OnResume() { } /// </summary>
/// <summary> protected virtual void OnPause()
/// Called before starting the shutdown of the application. {
/// </summary> }
protected virtual void OnTerminate() { }
/// <summary> /// <summary>
/// This function initializices everything in EFL and runs your application. /// Called before an application is used again after a call to OnPause().
/// This call will result in a call to OnInitialize(), which you application should override. /// </summary>
/// </summary> protected virtual void OnResume()
public void Launch(Efl.Csharp.Components components=Components.Ui) { {
}
/// <summary>
/// Called before starting the shutdown of the application.
/// </summary>
protected virtual void OnTerminate()
{
}
/// <summary>
/// This function initializices everything in EFL and runs your application.
/// This call will result in a call to OnInitialize(), which you application should override.
/// </summary>
public void Launch(Efl.Csharp.Components components = Components.Ui)
{
Init(components); Init(components);
Efl.App app = Efl.App.AppMain; Efl.App app = Efl.App.AppMain;
Eina.Array<String> command_line = new Eina.Array<String>(); Eina.Array<String> command_line = new Eina.Array<String>();
@ -103,26 +135,32 @@ namespace Efl {
#if EFL_BETA #if EFL_BETA
app.SetCommandArray(command_line); app.SetCommandArray(command_line);
#endif #endif
app.ArgumentsEvt += (object sender, LoopArgumentsEvt_Args evt) => { app.ArgumentsEvt += (object sender, LoopArgumentsEvt_Args evt) =>
if (evt.arg.Initialization) { {
OnInitialize(evt.arg.Argv); if (evt.arg.Initialization)
} {
OnArguments(evt.arg); OnInitialize(evt.arg.Argv);
}
OnArguments(evt.arg);
}; };
app.PauseEvt += (object sender, EventArgs e) => { app.PauseEvt += (object sender, EventArgs e) =>
OnPause(); {
OnPause();
}; };
app.ResumeEvt += (object sender, EventArgs e) => { app.ResumeEvt += (object sender, EventArgs e) =>
OnResume(); {
OnResume();
}; };
app.TerminateEvt += (object sender, EventArgs e) => { app.TerminateEvt += (object sender, EventArgs e) =>
OnTerminate(); {
OnTerminate();
}; };
app.Begin(); app.Begin();
Shutdown(); Shutdown();
}
} }
}
} }
}
}

View File

@ -8,13 +8,6 @@ bash = find_program('bash')
map = run_command('map_generate.sh').stdout() map = run_command('map_generate.sh').stdout()
efl_mono_lib = library('eflcustomexportsmono',
join_paths('..', '..', '..', 'lib', 'efl_mono', 'efl_custom_exports_mono.c'),
install : true,
install_dir : join_paths(dir_lib, 'efl-mono-'+version_major),
dependencies : [eo, eina]
)
efl_libs = configuration_data() efl_libs = configuration_data()
efl_libs.set('EFL_MONO_LIBRARY_MAP', map) efl_libs.set('EFL_MONO_LIBRARY_MAP', map)
efl_libs.set('CUSTOM_EXPORTS_MONO_DL_MONO', 'eflcustomexportsmono') efl_libs.set('CUSTOM_EXPORTS_MONO_DL_MONO', 'eflcustomexportsmono')

View File

@ -7,7 +7,8 @@ using static Eina.TraitFunctions;
using static Eina.AccessorNativeFunctions; using static Eina.AccessorNativeFunctions;
namespace Eina { namespace Eina
{
internal class AccessorNativeFunctions internal class AccessorNativeFunctions
{ {
@ -43,7 +44,7 @@ public class Accessor<T> : IEnumerable<T>, IDisposable
/// <summary>Create a new accessor wrapping the given pointer.</summary> /// <summary>Create a new accessor wrapping the given pointer.</summary>
/// <param name="handle">The native handle to be wrapped.</param> /// <param name="handle">The native handle to be wrapped.</param>
/// <param name="owner">Whether this wrapper owns the native accessor.</param> /// <param name="owner">Whether this wrapper owns the native accessor.</param>
public Accessor(IntPtr handle, Ownership owner=Ownership.Managed) public Accessor(IntPtr handle, Ownership owner = Ownership.Managed)
{ {
Handle = handle; Handle = handle;
Ownership = owner; Ownership = owner;
@ -53,7 +54,7 @@ public class Accessor<T> : IEnumerable<T>, IDisposable
/// <param name="handle">The native handle to be wrapped.</param> /// <param name="handle">The native handle to be wrapped.</param>
/// <param name="own">Whether this wrapper owns the native accessor.</param> /// <param name="own">Whether this wrapper owns the native accessor.</param>
/// <param name="ownContent">For compatibility with other EFL# containers. Ignored in acessors.</param> /// <param name="ownContent">For compatibility with other EFL# containers. Ignored in acessors.</param>
public Accessor(IntPtr handle, bool own, bool ownContent=false) public Accessor(IntPtr handle, bool own, bool ownContent = false)
: this(handle, own ? Ownership.Managed : Ownership.Unmanaged) : this(handle, own ? Ownership.Managed : Ownership.Unmanaged)
{ {
} }
@ -71,7 +72,14 @@ public class Accessor<T> : IEnumerable<T>, IDisposable
{ {
if (Ownership == Ownership.Managed && Handle != IntPtr.Zero) if (Ownership == Ownership.Managed && Handle != IntPtr.Zero)
{ {
eina_accessor_free(Handle); if (disposing)
{
eina_accessor_free(Handle);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_accessor_free, Handle);
}
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
} }
} }
@ -96,13 +104,16 @@ public class Accessor<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
if (Handle == IntPtr.Zero) if (Handle == IntPtr.Zero)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
IntPtr tmp = MemoryNative.Alloc(Marshal.SizeOf(typeof(IntPtr))); IntPtr tmp = MemoryNative.Alloc(Marshal.SizeOf(typeof(IntPtr)));
uint position = 0; uint position = 0;
try try
{ {
while(eina_accessor_data_get(Handle, position, tmp)) while (eina_accessor_data_get(Handle, position, tmp))
{ {
IntPtr data = (IntPtr)Marshal.PtrToStructure(tmp, typeof(IntPtr)); IntPtr data = (IntPtr)Marshal.PtrToStructure(tmp, typeof(IntPtr));
yield return Convert(data); yield return Convert(data);
@ -124,11 +135,12 @@ public class Accessor<T> : IEnumerable<T>, IDisposable
///<summary>Accessor for Inlists.</summary> ///<summary>Accessor for Inlists.</summary>
public class AccessorInList<T> : Accessor<T> public class AccessorInList<T> : Accessor<T>
{ {
/// <summary>Create a new accessor wrapping the given pointer.</summary> /// <summary>Create a new accessor wrapping the given pointer.</summary>
/// <param name="handle">The native handle to be wrapped.</param> /// <param name="handle">The native handle to be wrapped.</param>
/// <param name="own">Whether this wrapper owns the native accessor.</param> /// <param name="own">Whether this wrapper owns the native accessor.</param>
public AccessorInList(IntPtr handle, Ownership own): base(handle, own) {} public AccessorInList(IntPtr handle, Ownership own) : base(handle, own)
{
}
/// <summary>Convert the native data into managed. This is used when returning the data through a /// <summary>Convert the native data into managed. This is used when returning the data through a
/// <see cref="System.Collections.Generic.IEnumerator&lt;T&gt;"/>.</summary> /// <see cref="System.Collections.Generic.IEnumerator&lt;T&gt;"/>.</summary>
@ -146,7 +158,9 @@ public class AccessorInArray<T> : Accessor<T>
/// <summary>Create a new accessor wrapping the given pointer.</summary> /// <summary>Create a new accessor wrapping the given pointer.</summary>
/// <param name="handle">The native handle to be wrapped.</param> /// <param name="handle">The native handle to be wrapped.</param>
/// <param name="own">Whether this wrapper owns the native accessor.</param> /// <param name="own">Whether this wrapper owns the native accessor.</param>
public AccessorInArray(IntPtr handle, Ownership own): base(handle, own) {} public AccessorInArray(IntPtr handle, Ownership own) : base(handle, own)
{
}
/// <summary>Convert the native data into managed. This is used when returning the data through a /// <summary>Convert the native data into managed. This is used when returning the data through a
/// <see cref="System.Collections.Generic.IEnumerator&lt;T&gt;"/>.</summary> /// <see cref="System.Collections.Generic.IEnumerator&lt;T&gt;"/>.</summary>

View File

@ -7,7 +7,8 @@ using System.Collections.Generic;
using static Eina.TraitFunctions; using static Eina.TraitFunctions;
using static Eina.ArrayNativeFunctions; using static Eina.ArrayNativeFunctions;
namespace Eina { namespace Eina
{
public static class ArrayNativeFunctions public static class ArrayNativeFunctions
{ {
@ -64,7 +65,9 @@ public class Array<T> : IEnumerable<T>, IDisposable
Own = true; Own = true;
OwnContent = true; OwnContent = true;
if (Handle == IntPtr.Zero) if (Handle == IntPtr.Zero)
{
throw new SEHException("Could not alloc array"); throw new SEHException("Could not alloc array");
}
} }
internal bool InternalPush(IntPtr ele) internal bool InternalPush(IntPtr ele)
@ -99,6 +102,11 @@ public class Array<T> : IEnumerable<T>, IDisposable
public Array(IntPtr handle, bool own) public Array(IntPtr handle, bool own)
{ {
if (handle == IntPtr.Zero)
{
throw new ArgumentNullException("Handle can't be null");
}
Handle = handle; Handle = handle;
Own = own; Own = own;
OwnContent = own; OwnContent = own;
@ -106,6 +114,11 @@ public class Array<T> : IEnumerable<T>, IDisposable
public Array(IntPtr handle, bool own, bool ownContent) public Array(IntPtr handle, bool own, bool ownContent)
{ {
if (handle == IntPtr.Zero)
{
throw new ArgumentNullException("Handle can't be null");
}
Handle = handle; Handle = handle;
Own = own; Own = own;
OwnContent = ownContent; OwnContent = ownContent;
@ -121,19 +134,30 @@ public class Array<T> : IEnumerable<T>, IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (OwnContent) if (OwnContent)
{ {
int len = (int)eina_array_count_custom_export_mono(h); int len = (int)eina_array_count_custom_export_mono(h);
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
NativeFree<T>(eina_array_data_get_custom_export_mono(h, (uint)i)); NativeFree<T>(eina_array_data_get_custom_export_mono(h, (uint)i));
} }
} }
if (Own) if (Own)
eina_array_free(h); {
if (disposing)
{
eina_array_free(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_array_free, h);
}
}
} }
public void Dispose() public void Dispose()
@ -159,7 +183,7 @@ public class Array<T> : IEnumerable<T>, IDisposable
if (OwnContent) if (OwnContent)
{ {
int len = Length; int len = Length;
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
NativeFree<T>(InternalDataGet(i)); NativeFree<T>(InternalDataGet(i));
} }
@ -180,7 +204,7 @@ public class Array<T> : IEnumerable<T>, IDisposable
public int Count() public int Count()
{ {
return (int) eina_array_count_custom_export_mono(Handle); return (int)eina_array_count_custom_export_mono(Handle);
} }
public void SetOwnership(bool ownAll) public void SetOwnership(bool ownAll)
@ -200,7 +224,10 @@ public class Array<T> : IEnumerable<T>, IDisposable
IntPtr ele = ManagedToNativeAlloc(val); IntPtr ele = ManagedToNativeAlloc(val);
var r = InternalPush(ele); var r = InternalPush(ele);
if (!r) if (!r)
{
NativeFree<T>(ele); NativeFree<T>(ele);
}
return r; return r;
} }
@ -208,7 +235,9 @@ public class Array<T> : IEnumerable<T>, IDisposable
// public void Add(T val) // public void Add(T val)
// { // {
// if (!Push(val)) // if (!Push(val))
// throw; // {
// throw;
// }
// } // }
public T Pop() public T Pop()
@ -216,7 +245,10 @@ public class Array<T> : IEnumerable<T>, IDisposable
IntPtr ele = InternalPop(); IntPtr ele = InternalPop();
var r = NativeToManaged<T>(ele); var r = NativeToManaged<T>(ele);
if (OwnContent && ele != IntPtr.Zero) if (OwnContent && ele != IntPtr.Zero)
{
NativeFree<T>(ele); NativeFree<T>(ele);
}
return r; return r;
} }
@ -235,7 +267,10 @@ public class Array<T> : IEnumerable<T>, IDisposable
{ {
IntPtr ele = InternalDataGet(idx); // TODO: check bondaries ?? IntPtr ele = InternalDataGet(idx); // TODO: check bondaries ??
if (OwnContent && ele != IntPtr.Zero) if (OwnContent && ele != IntPtr.Zero)
{
NativeFree<T>(ele); NativeFree<T>(ele);
}
ele = ManagedToNativeAlloc(val); ele = ManagedToNativeAlloc(val);
InternalDataSet(idx, ele); InternalDataSet(idx, ele);
} }
@ -256,18 +291,24 @@ public class Array<T> : IEnumerable<T>, IDisposable
{ {
int len = Length; int len = Length;
var managed = new T[len]; var managed = new T[len];
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
managed[i] = DataGet(i); managed[i] = DataGet(i);
} }
return managed; return managed;
} }
public bool Append(T[] values) public bool Append(T[] values)
{ {
foreach(T v in values) foreach (T v in values)
{
if (!Push(v)) if (!Push(v))
{
return false; return false;
}
}
return true; return true;
} }
@ -280,7 +321,7 @@ public class Array<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
int len = Length; int len = Length;
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
yield return DataGet(i); yield return DataGet(i);
} }

View File

@ -3,7 +3,8 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Eina { namespace Eina
{
public class Binbuf : IDisposable public class Binbuf : IDisposable
{ {
@ -43,7 +44,7 @@ public class Binbuf : IDisposable
public int Length public int Length
{ {
get { return (int) GetLength(); } get { return (int)GetLength(); }
} }
private void InitNew() private void InitNew()
@ -51,7 +52,9 @@ public class Binbuf : IDisposable
Handle = eina_binbuf_new(); Handle = eina_binbuf_new();
Own = true; Own = true;
if (Handle == IntPtr.Zero) if (Handle == IntPtr.Zero)
{
throw new SEHException("Could not alloc binbuf"); throw new SEHException("Could not alloc binbuf");
}
} }
public Binbuf() public Binbuf()
@ -98,8 +101,16 @@ public class Binbuf : IDisposable
{ {
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (Own && h != IntPtr.Zero) { if (Own && h != IntPtr.Zero)
eina_binbuf_free(Handle); {
if (disposing)
{
eina_binbuf_free(Handle);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_binbuf_free, Handle);
}
} }
} }
@ -180,7 +191,9 @@ public class Binbuf : IDisposable
{ {
var ptr = eina_binbuf_string_get(Handle); var ptr = eina_binbuf_string_get(Handle);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
return null; return null;
}
var size = (int)(this.GetLength()); var size = (int)(this.GetLength());
byte[] mArray = new byte[size]; byte[] mArray = new byte[size];

View File

@ -6,6 +6,7 @@ using System.Runtime.InteropServices;
namespace Eina namespace Eina
{ {
namespace Callbacks namespace Callbacks
{ {
@ -41,7 +42,8 @@ internal static class NativeCustomExportFunctions
} }
/// <summary>Wrapper around native memory DllImport'd functions</summary> /// <summary>Wrapper around native memory DllImport'd functions</summary>
public static class MemoryNative { public static class MemoryNative
{
public static void Free(IntPtr ptr) public static void Free(IntPtr ptr)
{ {
NativeCustomExportFunctions.efl_mono_native_free(ptr); NativeCustomExportFunctions.efl_mono_native_free(ptr);
@ -122,7 +124,9 @@ public static class StringConversion
public static IntPtr ManagedStringToNativeUtf8Alloc(string managedString) public static IntPtr ManagedStringToNativeUtf8Alloc(string managedString)
{ {
if (managedString == null) if (managedString == null)
{
return IntPtr.Zero; return IntPtr.Zero;
}
byte[] strbuf = Encoding.UTF8.GetBytes(managedString); byte[] strbuf = Encoding.UTF8.GetBytes(managedString);
IntPtr native = MemoryNative.Alloc(strbuf.Length + 1); IntPtr native = MemoryNative.Alloc(strbuf.Length + 1);
@ -134,11 +138,15 @@ public static class StringConversion
public static string NativeUtf8ToManagedString(IntPtr pNativeData) public static string NativeUtf8ToManagedString(IntPtr pNativeData)
{ {
if (pNativeData == IntPtr.Zero) if (pNativeData == IntPtr.Zero)
{
return null; return null;
}
int len = 0; int len = 0;
while (Marshal.ReadByte(pNativeData, len) != 0) while (Marshal.ReadByte(pNativeData, len) != 0)
{
++len; ++len;
}
byte[] strbuf = new byte[len]; byte[] strbuf = new byte[len];
Marshal.Copy(pNativeData, strbuf, 0, strbuf.Length); Marshal.Copy(pNativeData, strbuf, 0, strbuf.Length);
@ -147,7 +155,8 @@ public static class StringConversion
} }
/// <summary>Enum to handle resource ownership between managed and unmanaged code.</summary> /// <summary>Enum to handle resource ownership between managed and unmanaged code.</summary>
public enum Ownership { public enum Ownership
{
/// <summary> The resource is owned by the managed code. It should free the handle on disposal.</summary> /// <summary> The resource is owned by the managed code. It should free the handle on disposal.</summary>
Managed, Managed,
/// <summary> The resource is owned by the unmanaged code. It won't be freed on disposal.</summary> /// <summary> The resource is owned by the unmanaged code. It won't be freed on disposal.</summary>

View File

@ -3,18 +3,24 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Eina { namespace Eina
{
public class Config { public class Config
{
[DllImport(efl.Libs.Eina)] private static extern int eina_init(); [DllImport(efl.Libs.Eina)] private static extern int eina_init();
[DllImport(efl.Libs.Eina)] private static extern int eina_shutdown(); [DllImport(efl.Libs.Eina)] private static extern int eina_shutdown();
public static void Init() { public static void Init()
{
if (eina_init() == 0) if (eina_init() == 0)
{
throw (new Efl.EflException("Failed to initialize Eina")); throw (new Efl.EflException("Failed to initialize Eina"));
}
} }
public static int Shutdown() { public static int Shutdown()
{
return eina_shutdown(); return eina_shutdown();
} }
@ -24,15 +30,15 @@ public class Config {
/// Wrapper class for pointers that need some cleanup afterwards /// Wrapper class for pointers that need some cleanup afterwards
/// like strings. /// like strings.
/// </summary> /// </summary>
public class DisposableIntPtr : IDisposable { public class DisposableIntPtr : IDisposable
{
public IntPtr Handle { get; set; } public IntPtr Handle { get; set; }
private bool ShouldFree; private bool ShouldFree;
private bool Disposed; private bool Disposed;
/// <summary>Wraps a new ptr what will be freed based on the /// <summary>Wraps a new ptr what will be freed based on the
/// value of shouldFree</summary> /// value of shouldFree</summary>
public DisposableIntPtr(IntPtr ptr, bool shouldFree=false) public DisposableIntPtr(IntPtr ptr, bool shouldFree = false)
{ {
Handle = ptr; Handle = ptr;
ShouldFree = shouldFree; ShouldFree = shouldFree;
@ -46,9 +52,11 @@ public class DisposableIntPtr : IDisposable {
protected virtual void Dispose(bool disposing) protected virtual void Dispose(bool disposing)
{ {
if (!Disposed && ShouldFree) { if (!Disposed && ShouldFree)
{
MemoryNative.Free(this.Handle); MemoryNative.Free(this.Handle);
} }
Disposed = true; Disposed = true;
} }
@ -57,4 +65,5 @@ public class DisposableIntPtr : IDisposable {
Dispose(false); Dispose(false);
} }
} }
} }

View File

@ -4,6 +4,7 @@ using System;
using System.Linq; using System.Linq;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using System.Collections.Generic; using System.Collections.Generic;
using System.Reflection;
using Eina.Callbacks; using Eina.Callbacks;
using static Eina.HashNativeFunctions; using static Eina.HashNativeFunctions;
@ -11,9 +12,15 @@ using static Eina.InarrayNativeFunctions;
using static Eina.InlistNativeFunctions; using static Eina.InlistNativeFunctions;
using static Eina.NativeCustomExportFunctions; using static Eina.NativeCustomExportFunctions;
namespace Eina { namespace Eina
{
public enum ElementType { NumericType, StringType, ObjectType }; public enum ElementType
{
NumericType,
StringType,
ObjectType
};
[StructLayout(LayoutKind.Sequential)] [StructLayout(LayoutKind.Sequential)]
public struct InlistMem public struct InlistMem
@ -82,13 +89,18 @@ public class StringElementTraits : IBaseElementTraits<string>
public void NativeFree(IntPtr nat) public void NativeFree(IntPtr nat)
{ {
if (nat != IntPtr.Zero) if (nat != IntPtr.Zero)
{
MemoryNative.Free(nat); MemoryNative.Free(nat);
}
} }
public void NativeFreeInlistNodeElement(IntPtr nat) public void NativeFreeInlistNodeElement(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return; return;
}
var val = Marshal.PtrToStructure<IntPtr> var val = Marshal.PtrToStructure<IntPtr>
(nat + Marshal.SizeOf<InlistMem>()); (nat + Marshal.SizeOf<InlistMem>());
NativeFree(val); NativeFree(val);
@ -97,9 +109,15 @@ public class StringElementTraits : IBaseElementTraits<string>
public void NativeFreeInlistNode(IntPtr nat, bool freeElement) public void NativeFreeInlistNode(IntPtr nat, bool freeElement)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return; return;
}
if (freeElement) if (freeElement)
{
NativeFreeInlistNodeElement(nat); NativeFreeInlistNodeElement(nat);
}
MemoryNative.Free(nat); MemoryNative.Free(nat);
} }
@ -115,7 +133,10 @@ public class StringElementTraits : IBaseElementTraits<string>
public string NativeToManaged(IntPtr nat) public string NativeToManaged(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(string); return default(string);
}
return StringConversion.NativeUtf8ToManagedString(nat); return StringConversion.NativeUtf8ToManagedString(nat);
} }
@ -126,6 +147,7 @@ public class StringElementTraits : IBaseElementTraits<string>
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(string); return default(string);
} }
IntPtr ptr_location = nat + Marshal.SizeOf<InlistMem>(); IntPtr ptr_location = nat + Marshal.SizeOf<InlistMem>();
return NativeToManaged(Marshal.ReadIntPtr(ptr_location)); return NativeToManaged(Marshal.ReadIntPtr(ptr_location));
} }
@ -134,10 +156,16 @@ public class StringElementTraits : IBaseElementTraits<string>
public string NativeToManagedInplace(IntPtr nat) public string NativeToManagedInplace(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(string); return default(string);
}
nat = Marshal.ReadIntPtr(nat); nat = Marshal.ReadIntPtr(nat);
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(string); return default(string);
}
return NativeToManaged(nat); return NativeToManaged(nat);
} }
@ -169,18 +197,14 @@ public class StringElementTraits : IBaseElementTraits<string>
public class EflObjectElementTraits<T> : IBaseElementTraits<T> public class EflObjectElementTraits<T> : IBaseElementTraits<T>
{ {
private System.Type concreteType = null;
public EflObjectElementTraits(System.Type concrete)
{
concreteType = concrete;
}
public IntPtr ManagedToNativeAlloc(T man) public IntPtr ManagedToNativeAlloc(T man)
{ {
IntPtr h = ((Efl.Eo.IWrapper)man).NativeHandle; IntPtr h = ((Efl.Eo.IWrapper)man).NativeHandle;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return h; return h;
}
return Efl.Eo.Globals.efl_ref(h); return Efl.Eo.Globals.efl_ref(h);
} }
@ -204,19 +228,26 @@ public class EflObjectElementTraits<T> : IBaseElementTraits<T>
public void NativeFree(IntPtr nat) public void NativeFree(IntPtr nat)
{ {
if (nat != IntPtr.Zero) if (nat != IntPtr.Zero)
Efl.Eo.Globals.efl_unref(nat); {
Efl.Eo.Globals.efl_mono_thread_safe_efl_unref(nat);
}
} }
public void NativeFreeRef(IntPtr nat, bool unrefs) public void NativeFreeRef(IntPtr nat, bool unrefs)
{ {
if (unrefs) if (unrefs)
{
NativeFree(nat); NativeFree(nat);
}
} }
public void NativeFreeInlistNodeElement(IntPtr nat) public void NativeFreeInlistNodeElement(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return; return;
}
var val = Marshal.PtrToStructure<IntPtr> var val = Marshal.PtrToStructure<IntPtr>
(nat + Marshal.SizeOf<InlistMem>()); (nat + Marshal.SizeOf<InlistMem>());
NativeFree(val); NativeFree(val);
@ -225,9 +256,15 @@ public class EflObjectElementTraits<T> : IBaseElementTraits<T>
public void NativeFreeInlistNode(IntPtr nat, bool freeElement) public void NativeFreeInlistNode(IntPtr nat, bool freeElement)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return; return;
}
if (freeElement) if (freeElement)
{
NativeFreeInlistNodeElement(nat); NativeFreeInlistNodeElement(nat);
}
MemoryNative.Free(nat); MemoryNative.Free(nat);
} }
@ -243,14 +280,20 @@ public class EflObjectElementTraits<T> : IBaseElementTraits<T>
public T NativeToManaged(IntPtr nat) public T NativeToManaged(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(T); return default(T);
return (T) Activator.CreateInstance(concreteType, Efl.Eo.Globals.efl_ref(nat)); }
return (T) Efl.Eo.Globals.CreateWrapperFor(nat, shouldIncRef: true);
} }
public T NativeToManagedRef(IntPtr nat) public T NativeToManagedRef(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(T); return default(T);
}
return NativeToManaged(nat); return NativeToManaged(nat);
} }
@ -261,6 +304,7 @@ public class EflObjectElementTraits<T> : IBaseElementTraits<T>
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(T); return default(T);
} }
IntPtr ptr_location = nat + Marshal.SizeOf<InlistMem>(); IntPtr ptr_location = nat + Marshal.SizeOf<InlistMem>();
return NativeToManaged(Marshal.ReadIntPtr(ptr_location)); return NativeToManaged(Marshal.ReadIntPtr(ptr_location));
} }
@ -269,10 +313,16 @@ public class EflObjectElementTraits<T> : IBaseElementTraits<T>
public T NativeToManagedInplace(IntPtr nat) public T NativeToManagedInplace(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(T); return default(T);
}
nat = Marshal.ReadIntPtr(nat); nat = Marshal.ReadIntPtr(nat);
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
{
return default(T); return default(T);
}
return NativeToManaged(nat); return NativeToManaged(nat);
} }
@ -355,6 +405,7 @@ public abstract class PrimitiveElementTraits<T>
Eina.Log.Error("Null pointer on primitive/struct container."); Eina.Log.Error("Null pointer on primitive/struct container.");
return default(T); return default(T);
} }
return PrimitiveConversion.PointerToManaged<T>(nat); return PrimitiveConversion.PointerToManaged<T>(nat);
} }
@ -371,7 +422,7 @@ public abstract class PrimitiveElementTraits<T>
private int PrimitiveCompareCb(IntPtr ptr1, IntPtr ptr2) private int PrimitiveCompareCb(IntPtr ptr1, IntPtr ptr2)
{ {
var m1 = (IComparable) NativeToManaged(ptr1); var m1 = (IComparable)NativeToManaged(ptr1);
var m2 = NativeToManaged(ptr2); var m2 = NativeToManaged(ptr2);
return m1.CompareTo(m2); return m1.CompareTo(m2);
} }
@ -379,7 +430,10 @@ public abstract class PrimitiveElementTraits<T>
public IntPtr EinaCompareCb() public IntPtr EinaCompareCb()
{ {
if (dlgt == null) if (dlgt == null)
{
dlgt = new Eina_Compare_Cb(PrimitiveCompareCb); dlgt = new Eina_Compare_Cb(PrimitiveCompareCb);
}
return Marshal.GetFunctionPointerForDelegate(dlgt); return Marshal.GetFunctionPointerForDelegate(dlgt);
} }
@ -406,10 +460,16 @@ abstract public class Primitive32ElementTraits<T> : PrimitiveElementTraits<T>, I
public Primitive32ElementTraits() public Primitive32ElementTraits()
{ {
if (int32Traits == null) if (int32Traits == null)
{
if (typeof(T) == typeof(Int32)) // avoid infinite recursion if (typeof(T) == typeof(Int32)) // avoid infinite recursion
{
int32Traits = (IBaseElementTraits<Int32>)this; int32Traits = (IBaseElementTraits<Int32>)this;
}
else else
{
int32Traits = TraitFunctions.GetTypeTraits<Int32>(); int32Traits = TraitFunctions.GetTypeTraits<Int32>();
}
}
} }
public abstract void ManagedToNativeCopyTo(T man, IntPtr mem); public abstract void ManagedToNativeCopyTo(T man, IntPtr mem);
@ -438,10 +498,16 @@ abstract public class Primitive64ElementTraits<T> : PrimitiveElementTraits<T>, I
public Primitive64ElementTraits() public Primitive64ElementTraits()
{ {
if (int64Traits == null) if (int64Traits == null)
{
if (typeof(T) == typeof(Int64)) // avoid infinite recursion if (typeof(T) == typeof(Int64)) // avoid infinite recursion
{
int64Traits = (IBaseElementTraits<Int64>)this; int64Traits = (IBaseElementTraits<Int64>)this;
}
else else
{
int64Traits = TraitFunctions.GetTypeTraits<Int64>(); int64Traits = TraitFunctions.GetTypeTraits<Int64>();
}
}
} }
public abstract void ManagedToNativeCopyTo(T man, IntPtr mem); public abstract void ManagedToNativeCopyTo(T man, IntPtr mem);
@ -471,6 +537,7 @@ public class IntElementTraits : Primitive32ElementTraits<int>, IBaseElementTrait
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public int NativeToManagedInlistNode(IntPtr nat) override public int NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -478,6 +545,7 @@ public class IntElementTraits : Primitive32ElementTraits<int>, IBaseElementTrait
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(int); return default(int);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new int[1]; var v = new int[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -493,6 +561,7 @@ public class CharElementTraits : Primitive32ElementTraits<char>, IBaseElementTra
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public char NativeToManagedInlistNode(IntPtr nat) override public char NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -500,12 +569,14 @@ public class CharElementTraits : Primitive32ElementTraits<char>, IBaseElementTra
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(char); return default(char);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new char[1]; var v = new char[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
return v[0]; return v[0];
} }
} }
public class LongElementTraits : Primitive64ElementTraits<long>, IBaseElementTraits<long> public class LongElementTraits : Primitive64ElementTraits<long>, IBaseElementTraits<long>
{ {
override public void ManagedToNativeCopyTo(long man, IntPtr mem) override public void ManagedToNativeCopyTo(long man, IntPtr mem)
@ -514,6 +585,7 @@ public class LongElementTraits : Primitive64ElementTraits<long>, IBaseElementTra
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public long NativeToManagedInlistNode(IntPtr nat) override public long NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -521,6 +593,7 @@ public class LongElementTraits : Primitive64ElementTraits<long>, IBaseElementTra
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(long); return default(long);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new long[1]; var v = new long[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -536,6 +609,7 @@ public class ShortElementTraits : Primitive32ElementTraits<short>, IBaseElementT
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public short NativeToManagedInlistNode(IntPtr nat) override public short NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -543,6 +617,7 @@ public class ShortElementTraits : Primitive32ElementTraits<short>, IBaseElementT
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(short); return default(short);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new short[1]; var v = new short[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -558,6 +633,7 @@ public class FloatElementTraits : Primitive32ElementTraits<float>, IBaseElementT
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public float NativeToManagedInlistNode(IntPtr nat) override public float NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -565,6 +641,7 @@ public class FloatElementTraits : Primitive32ElementTraits<float>, IBaseElementT
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(float); return default(float);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new float[1]; var v = new float[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -580,6 +657,7 @@ public class DoubleElementTraits : Primitive64ElementTraits<double>, IBaseElemen
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public double NativeToManagedInlistNode(IntPtr nat) override public double NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -587,6 +665,7 @@ public class DoubleElementTraits : Primitive64ElementTraits<double>, IBaseElemen
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(double); return default(double);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new double[1]; var v = new double[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -602,6 +681,7 @@ public class ByteElementTraits : Primitive32ElementTraits<byte>, IBaseElementTra
arr[0] = man; arr[0] = man;
Marshal.Copy(arr, 0, mem, 1); Marshal.Copy(arr, 0, mem, 1);
} }
override public byte NativeToManagedInlistNode(IntPtr nat) override public byte NativeToManagedInlistNode(IntPtr nat)
{ {
if (nat == IntPtr.Zero) if (nat == IntPtr.Zero)
@ -609,6 +689,7 @@ public class ByteElementTraits : Primitive32ElementTraits<byte>, IBaseElementTra
Eina.Log.Error("Null pointer for Inlist node."); Eina.Log.Error("Null pointer for Inlist node.");
return default(byte); return default(byte);
} }
IntPtr loc = nat + Marshal.SizeOf<InlistMem>(); IntPtr loc = nat + Marshal.SizeOf<InlistMem>();
var v = new byte[1]; var v = new byte[1];
Marshal.Copy(loc, v, 0, 1); Marshal.Copy(loc, v, 0, 1);
@ -631,11 +712,17 @@ public static class TraitFunctions
public static Eina.ElementType GetElementTypeCode(System.Type type) public static Eina.ElementType GetElementTypeCode(System.Type type)
{ {
if (IsEflObject(type)) if (IsEflObject(type))
{
return ElementType.ObjectType; return ElementType.ObjectType;
}
else if (IsString(type)) else if (IsString(type))
{
return ElementType.StringType; return ElementType.StringType;
}
else else
{
return ElementType.NumericType; return ElementType.NumericType;
}
} }
private static IDictionary<System.Type, object> register = new Dictionary<System.Type, object>(); private static IDictionary<System.Type, object> register = new Dictionary<System.Type, object>();
@ -643,7 +730,9 @@ public static class TraitFunctions
private static System.Type AsEflInstantiableType(System.Type type) private static System.Type AsEflInstantiableType(System.Type type)
{ {
if (!IsEflObject(type)) if (!IsEflObject(type))
{
return null; return null;
}
if (type.IsInterface) if (type.IsInterface)
{ {
@ -663,32 +752,57 @@ public static class TraitFunctions
{ {
System.Type concrete = AsEflInstantiableType(type); System.Type concrete = AsEflInstantiableType(type);
if (concrete == null || !type.IsAssignableFrom(concrete)) if (concrete == null || !type.IsAssignableFrom(concrete))
{
throw new Exception("Failed to get a suitable concrete class for this type."); throw new Exception("Failed to get a suitable concrete class for this type.");
traits = new EflObjectElementTraits<T>(concrete); }
// No need to pass concrete as the traits class will use reflection to get the actually most
// derived type returned.
traits = new EflObjectElementTraits<T>();
} }
else if (IsString(type)) else if (IsString(type))
{
traits = new StringElementTraits(); traits = new StringElementTraits();
}
else if (type.IsValueType) else if (type.IsValueType)
{ {
if (type == typeof(int)) if (type == typeof(int))
{
traits = new IntElementTraits(); traits = new IntElementTraits();
}
else if (type == typeof(char)) else if (type == typeof(char))
{
traits = new CharElementTraits(); traits = new CharElementTraits();
}
else if (type == typeof(long)) else if (type == typeof(long))
{
traits = new LongElementTraits(); traits = new LongElementTraits();
}
else if (type == typeof(short)) else if (type == typeof(short))
{
traits = new ShortElementTraits(); traits = new ShortElementTraits();
}
else if (type == typeof(float)) else if (type == typeof(float))
{
traits = new FloatElementTraits(); traits = new FloatElementTraits();
}
else if (type == typeof(double)) else if (type == typeof(double))
{
traits = new DoubleElementTraits(); traits = new DoubleElementTraits();
}
else if (type == typeof(byte)) else if (type == typeof(byte))
{
traits = new ByteElementTraits(); traits = new ByteElementTraits();
}
else else
{
throw new Exception("No traits registered for this type"); throw new Exception("No traits registered for this type");
}
} }
else else
{
throw new Exception("No traits registered for this type"); throw new Exception("No traits registered for this type");
}
register[type] = traits; register[type] = traits;
return traits; return traits;
@ -704,8 +818,11 @@ public static class TraitFunctions
{ {
object traits; object traits;
if (!register.TryGetValue(typeof(T), out traits)) if (!register.TryGetValue(typeof(T), out traits))
{
traits = RegisterTypeTraits<T>(); traits = RegisterTypeTraits<T>();
return (IBaseElementTraits<T>) traits; }
return (IBaseElementTraits<T>)traits;
} }
// // // //

View File

@ -3,7 +3,8 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Eina { namespace Eina
{
public struct Error : IComparable<Error> public struct Error : IComparable<Error>
{ {
@ -21,19 +22,26 @@ public struct Error : IComparable<Error>
public static Error ENOENT = new Error(2); public static Error ENOENT = new Error(2);
public static Error ECANCELED = new Error(125); public static Error ECANCELED = new Error(125);
public Error(int value) { code = value; } public Error(int value)
{
code = value;
}
static public implicit operator Error(int val) static public implicit operator Error(int val)
{ {
return new Error(val); return new Error(val);
} }
static public implicit operator int(Error error) static public implicit operator int(Error error)
{ {
return error.code; return error.code;
} }
public int CompareTo(Error err) public int CompareTo(Error err)
{ {
return code.CompareTo(err.code); return code.CompareTo(err.code);
} }
public override string ToString() public override string ToString()
{ {
return "Eina.Error(" + code + ")"; return "Eina.Error(" + code + ")";
@ -80,7 +88,9 @@ public struct Error : IComparable<Error>
public static void Raise(Error e) public static void Raise(Error e)
{ {
if (e != 0) if (e != 0)
{
throw (new Efl.EflException(MsgGet(e))); throw (new Efl.EflException(MsgGet(e)));
}
} }
public static void Clear() public static void Clear()
@ -93,4 +103,5 @@ public struct Error : IComparable<Error>
return eina_error_msg_register(msg); return eina_error_msg_register(msg);
} }
} }
} }

View File

@ -137,8 +137,10 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
public bool OwnKey {get; set;} public bool OwnKey {get; set;}
public bool OwnValue {get; set;} public bool OwnValue {get; set;}
public int Count { public int Count
get { {
get
{
return Population(); return Population();
} }
} }
@ -179,10 +181,21 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (Own) if (Own)
eina_hash_free(h); {
if (disposing)
{
eina_hash_free(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_hash_free, h);
}
}
} }
public void Dispose() public void Dispose()
@ -218,7 +231,9 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
OwnValue = ownValue; OwnValue = ownValue;
if (ownValue) if (ownValue)
{
eina_hash_free_cb_set(Handle, EinaFreeCb<TValue>()); eina_hash_free_cb_set(Handle, EinaFreeCb<TValue>());
}
} }
public void SetOwnership(bool ownAll) public void SetOwnership(bool ownAll)
@ -289,7 +304,9 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
//NativeFreeRef<TKey>(nk); //NativeFreeRef<TKey>(nk);
FreeNativeIndirection<TKey>(gchnk, ForceRefKey<TKey>()); FreeNativeIndirection<TKey>(gchnk, ForceRefKey<TKey>());
if (found == IntPtr.Zero) if (found == IntPtr.Zero)
{
throw new KeyNotFoundException(); throw new KeyNotFoundException();
}
return NativeToManaged<TValue>(IndirectNative<TValue>(found, false)); return NativeToManaged<TValue>(IndirectNative<TValue>(found, false));
} }
@ -305,6 +322,7 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
val = default(TValue); val = default(TValue);
return false; return false;
} }
val = NativeToManaged<TValue>(IndirectNative<TValue>(found, false)); val = NativeToManaged<TValue>(IndirectNative<TValue>(found, false));
return true; return true;
} }
@ -334,8 +352,12 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
NativeFree<TValue>(nv); NativeFree<TValue>(nv);
return false; return false;
} }
if (OwnValue) if (OwnValue)
{
NativeFree<TValue>(old); NativeFree<TValue>(old);
}
return true; return true;
} }
@ -355,7 +377,7 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
return GCHandle.ToIntPtr(gch); return GCHandle.ToIntPtr(gch);
} }
else if(IsEflObject(typeof(T)) && forceRef) else if (IsEflObject(typeof(T)) && forceRef)
{ {
GCHandle gch = GCHandle.Alloc(new byte[Marshal.SizeOf<IntPtr>()], GCHandleType.Pinned); GCHandle gch = GCHandle.Alloc(new byte[Marshal.SizeOf<IntPtr>()], GCHandleType.Pinned);
IntPtr pin = gch.AddrOfPinnedObject(); IntPtr pin = gch.AddrOfPinnedObject();
@ -369,6 +391,7 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
return ManagedToNativeAlloc(value); return ManagedToNativeAlloc(value);
} }
} }
private static IntPtr GetNativePtr<T>(IntPtr gchptr, bool forceRef) private static IntPtr GetNativePtr<T>(IntPtr gchptr, bool forceRef)
{ {
if (forceRef) if (forceRef)
@ -383,6 +406,7 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
return gchptr; return gchptr;
} }
} }
private static void FreeNativeIndirection<T>(IntPtr gchptr, bool forceRef) private static void FreeNativeIndirection<T>(IntPtr gchptr, bool forceRef)
{ {
if (forceRef) if (forceRef)
@ -416,7 +440,9 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
FreeNativeIndirection<TKey>(gchnk, ForceRefKey<TKey>()); FreeNativeIndirection<TKey>(gchnk, ForceRefKey<TKey>());
FreeNativeIndirection<TValue>(gchnv, false); FreeNativeIndirection<TValue>(gchnv, false);
if (OwnValue || old != IntPtr.Zero) if (OwnValue || old != IntPtr.Zero)
{
NativeFree<TValue>(old); NativeFree<TValue>(old);
}
} }
public TValue this[TKey key] public TValue this[TKey key]
@ -494,4 +520,3 @@ public class Hash<TKey, TValue> : IEnumerable<KeyValuePair<TKey,TValue>>, IDi
} }
} }

View File

@ -7,7 +7,8 @@ using System.Collections.Generic;
using static Eina.TraitFunctions; using static Eina.TraitFunctions;
using static Eina.InarrayNativeFunctions; using static Eina.InarrayNativeFunctions;
namespace Eina { namespace Eina
{
public static class InarrayNativeFunctions public static class InarrayNativeFunctions
{ {
@ -86,7 +87,9 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
Own = true; Own = true;
OwnContent = true; OwnContent = true;
if (Handle == IntPtr.Zero) if (Handle == IntPtr.Zero)
{
throw new SEHException("Could not alloc inarray"); throw new SEHException("Could not alloc inarray");
}
} }
public Inarray() public Inarray()
@ -123,19 +126,30 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (OwnContent) if (OwnContent)
{ {
uint len = eina_inarray_count(h); uint len = eina_inarray_count(h);
for(uint i = 0; i < len; ++i) for (uint i = 0; i < len; ++i)
{ {
NativeFreeInplace<T>(eina_inarray_nth(h, i)); NativeFreeInplace<T>(eina_inarray_nth(h, i));
} }
} }
if (Own) if (Own)
eina_inarray_free(h); {
if (disposing)
{
eina_inarray_free(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_inarray_free, h);
}
}
} }
public void Dispose() public void Dispose()
@ -176,7 +190,7 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
public int Count() public int Count()
{ {
return (int) eina_inarray_count(Handle); return (int)eina_inarray_count(Handle);
} }
public void SetOwnership(bool ownAll) public void SetOwnership(bool ownAll)
@ -201,7 +215,10 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
var r = eina_inarray_push(Handle, ind); var r = eina_inarray_push(Handle, ind);
if (r == -1) if (r == -1)
{
NativeFreeInplace<T>(ele); NativeFreeInplace<T>(ele);
}
ResidueFreeInplace<T>(ele); ResidueFreeInplace<T>(ele);
gch.Free(); gch.Free();
return r; return r;
@ -211,7 +228,9 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
// public void Add(T val) // public void Add(T val)
// { // {
// if (!Push(val)) // if (!Push(val))
// throw; // {
// throw;
// }
// } // }
public T Pop() public T Pop()
@ -219,7 +238,10 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
IntPtr ele = eina_inarray_pop(Handle); IntPtr ele = eina_inarray_pop(Handle);
var r = NativeToManagedInplace<T>(ele); var r = NativeToManagedInplace<T>(ele);
if (OwnContent && ele != IntPtr.Zero) if (OwnContent && ele != IntPtr.Zero)
{
NativeFreeInplace<T>(ele); NativeFreeInplace<T>(ele);
}
return r; return r;
} }
@ -244,7 +266,10 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
var r = eina_inarray_insert_at(Handle, idx, ind); var r = eina_inarray_insert_at(Handle, idx, ind);
if (!r) if (!r)
{
NativeFreeInplace<T>(ele); NativeFreeInplace<T>(ele);
}
ResidueFreeInplace<T>(ele); ResidueFreeInplace<T>(ele);
return r; return r;
} }
@ -253,9 +278,15 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
{ {
var old = eina_inarray_nth(Handle, idx); var old = eina_inarray_nth(Handle, idx);
if (old == IntPtr.Zero) if (old == IntPtr.Zero)
{
return false; return false;
}
if (OwnContent) if (OwnContent)
{
NativeFreeInplace<T>(old); NativeFreeInplace<T>(old);
}
var ele = IntPtr.Zero; var ele = IntPtr.Zero;
GCHandle gch = GCHandle.Alloc(ele, GCHandleType.Pinned); GCHandle gch = GCHandle.Alloc(ele, GCHandleType.Pinned);
IntPtr ind = gch.AddrOfPinnedObject(); IntPtr ind = gch.AddrOfPinnedObject();
@ -283,9 +314,14 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
{ {
IntPtr ele = eina_inarray_nth(Handle, idx); IntPtr ele = eina_inarray_nth(Handle, idx);
if (ele == IntPtr.Zero) if (ele == IntPtr.Zero)
{
return false; return false;
}
if (OwnContent) if (OwnContent)
{
NativeFreeInplace<T>(ele); NativeFreeInplace<T>(ele);
}
return eina_inarray_remove_at(Handle, idx); return eina_inarray_remove_at(Handle, idx);
} }
@ -299,18 +335,24 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
{ {
int len = Length; int len = Length;
var managed = new T[len]; var managed = new T[len];
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
managed[i] = At(i); managed[i] = At(i);
} }
return managed; return managed;
} }
public bool Append(T[] values) public bool Append(T[] values)
{ {
foreach(T v in values) foreach (T v in values)
{
if (Push(v) == -1) if (Push(v) == -1)
{
return false; return false;
}
}
return true; return true;
} }
@ -327,7 +369,7 @@ public class Inarray<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
int len = Length; int len = Length;
for(int i = 0; i < len; ++i) for (int i = 0; i < len; ++i)
{ {
yield return At(i); yield return At(i);
} }

View File

@ -8,7 +8,8 @@ using static Eina.TraitFunctions;
using static Eina.InlistNativeFunctions; using static Eina.InlistNativeFunctions;
using Eina.Callbacks; using Eina.Callbacks;
namespace Eina { namespace Eina
{
public static class InlistNativeFunctions public static class InlistNativeFunctions
{ {
@ -111,11 +112,16 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
private IntPtr InternalAt(int idx) private IntPtr InternalAt(int idx)
{ {
if (idx < 0) if (idx < 0)
{
return IntPtr.Zero; return IntPtr.Zero;
}
IntPtr curr = Handle; IntPtr curr = Handle;
for (int n = 0; n != idx && curr != IntPtr.Zero; ++n) for (int n = 0; n != idx && curr != IntPtr.Zero; ++n)
{
curr = InternalNext(curr); curr = InternalNext(curr);
}
return curr; return curr;
} }
@ -159,11 +165,13 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (OwnContent) if (OwnContent)
{ {
for(IntPtr curr = h; curr != IntPtr.Zero; curr = InternalNext(curr)) for (IntPtr curr = h; curr != IntPtr.Zero; curr = InternalNext(curr))
{ {
NativeFreeInlistNodeElement<T>(curr); NativeFreeInlistNodeElement<T>(curr);
} }
@ -212,7 +220,7 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
public int Count() public int Count()
{ {
return (int) eina_inlist_count(Handle); return (int)eina_inlist_count(Handle);
} }
public void Clean() public void Clean()
@ -248,7 +256,10 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
{ {
IntPtr node = InternalAt(idx); IntPtr node = InternalAt(idx);
if (node == IntPtr.Zero) if (node == IntPtr.Zero)
{
throw new IndexOutOfRangeException(); throw new IndexOutOfRangeException();
}
return NativeToManagedInlistNode<T>(node); return NativeToManagedInlistNode<T>(node);
} }
@ -256,7 +267,9 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
{ {
IntPtr old = InternalAt(idx); IntPtr old = InternalAt(idx);
if (old == IntPtr.Zero) if (old == IntPtr.Zero)
{
throw new IndexOutOfRangeException(); throw new IndexOutOfRangeException();
}
IntPtr new_node = ManagedToNativeAllocInlistNode(val); IntPtr new_node = ManagedToNativeAllocInlistNode(val);
@ -282,17 +295,20 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
{ {
var managed = new T[Count()]; var managed = new T[Count()];
int i = 0; int i = 0;
for(IntPtr curr = Handle; curr != IntPtr.Zero; ++i, curr = InternalNext(curr)) for (IntPtr curr = Handle; curr != IntPtr.Zero; ++i, curr = InternalNext(curr))
{ {
managed[i] = NativeToManagedInlistNode<T>(curr); managed[i] = NativeToManagedInlistNode<T>(curr);
} }
return managed; return managed;
} }
public void AppendArray(T[] values) public void AppendArray(T[] values)
{ {
foreach (T v in values) foreach (T v in values)
{
Append(v); Append(v);
}
} }
@ -303,7 +319,7 @@ public class Inlist<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
for(IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr)) for (IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr))
{ {
yield return NativeToManagedInlistNode<T>(curr); yield return NativeToManagedInlistNode<T>(curr);
} }

View File

@ -7,7 +7,8 @@ using System.Collections.Generic;
using static Eina.TraitFunctions; using static Eina.TraitFunctions;
using static Eina.IteratorNativeFunctions; using static Eina.IteratorNativeFunctions;
namespace Eina { namespace Eina
{
public static class IteratorNativeFunctions public static class IteratorNativeFunctions
{ {
@ -58,18 +59,29 @@ public class Iterator<T> : IEnumerable<T>, IDisposable
var h = Handle; var h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (OwnContent) if (OwnContent)
{ {
for(IntPtr data; eina_iterator_next(h, out data);) for (IntPtr data; eina_iterator_next(h, out data);)
{ {
NativeFree<T>(data); NativeFree<T>(data);
} }
} }
if (Own) if (Own)
eina_iterator_free(h); {
if (disposing)
{
eina_iterator_free(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_iterator_free, h);
}
}
} }
public void Dispose() public void Dispose()
@ -114,7 +126,9 @@ public class Iterator<T> : IEnumerable<T>, IDisposable
res = NativeToManaged<T>(data); res = NativeToManaged<T>(data);
if (OwnContent) if (OwnContent)
{
NativeFree<T>(data); NativeFree<T>(data);
}
return true; return true;
} }
@ -131,7 +145,7 @@ public class Iterator<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
for(T curr; Next(out curr);) for (T curr; Next(out curr);)
{ {
yield return curr; yield return curr;
} }

View File

@ -8,7 +8,8 @@ using static Eina.TraitFunctions;
using static Eina.ListNativeFunctions; using static Eina.ListNativeFunctions;
using Eina.Callbacks; using Eina.Callbacks;
namespace Eina { namespace Eina
{
public static class ListNativeFunctions public static class ListNativeFunctions
{ {
@ -44,6 +45,8 @@ public static class ListNativeFunctions
eina_list_move_list(ref IntPtr to, ref IntPtr from, IntPtr data); eina_list_move_list(ref IntPtr to, ref IntPtr from, IntPtr data);
[DllImport(efl.Libs.Eina)] public static extern IntPtr [DllImport(efl.Libs.Eina)] public static extern IntPtr
eina_list_free(IntPtr list); eina_list_free(IntPtr list);
[DllImport(efl.Libs.CustomExports)] public static extern void
efl_mono_thread_safe_eina_list_free(IntPtr list);
[DllImport(efl.Libs.Eina)] public static extern IntPtr [DllImport(efl.Libs.Eina)] public static extern IntPtr
eina_list_nth(IntPtr list, uint n); eina_list_nth(IntPtr list, uint n);
[DllImport(efl.Libs.Eina)] public static extern IntPtr [DllImport(efl.Libs.Eina)] public static extern IntPtr
@ -175,18 +178,29 @@ public class List<T> : IEnumerable<T>, IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (OwnContent) if (OwnContent)
{ {
for(IntPtr curr = h; curr != IntPtr.Zero; curr = InternalNext(curr)) for (IntPtr curr = h; curr != IntPtr.Zero; curr = InternalNext(curr))
{ {
NativeFree<T>(InternalDataGet(curr)); NativeFree<T>(InternalDataGet(curr));
} }
} }
if (Own) if (Own)
eina_list_free(h); {
if (disposing)
{
eina_list_free(h);
}
else
{
efl_mono_thread_safe_eina_list_free(h);
}
}
} }
public void Dispose() public void Dispose()
@ -221,7 +235,7 @@ public class List<T> : IEnumerable<T>, IDisposable
public int Count() public int Count()
{ {
return (int) eina_list_count_custom_export_mono(Handle); return (int)eina_list_count_custom_export_mono(Handle);
} }
public void Append(T val) public void Append(T val)
@ -274,9 +288,15 @@ public class List<T> : IEnumerable<T>, IDisposable
{ {
IntPtr pos = eina_list_nth_list(Handle, (uint)idx); IntPtr pos = eina_list_nth_list(Handle, (uint)idx);
if (pos == IntPtr.Zero) if (pos == IntPtr.Zero)
{
throw new IndexOutOfRangeException(); throw new IndexOutOfRangeException();
}
if (OwnContent) if (OwnContent)
{
NativeFree<T>(InternalDataGet(pos)); NativeFree<T>(InternalDataGet(pos));
}
IntPtr ele = ManagedToNativeAlloc(val); IntPtr ele = ManagedToNativeAlloc(val);
InternalDataSet(pos, ele); InternalDataSet(pos, ele);
} }
@ -314,17 +334,20 @@ public class List<T> : IEnumerable<T>, IDisposable
{ {
var managed = new T[Count()]; var managed = new T[Count()];
int i = 0; int i = 0;
for(IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr), ++i) for (IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr), ++i)
{ {
managed[i] = NativeToManaged<T>(InternalDataGet(curr)); managed[i] = NativeToManaged<T>(InternalDataGet(curr));
} }
return managed; return managed;
} }
public void AppendArray(T[] values) public void AppendArray(T[] values)
{ {
foreach (T v in values) foreach (T v in values)
{
Append(v); Append(v);
}
} }
@ -340,7 +363,7 @@ public class List<T> : IEnumerable<T>, IDisposable
public IEnumerator<T> GetEnumerator() public IEnumerator<T> GetEnumerator()
{ {
for(IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr)) for (IntPtr curr = Handle; curr != IntPtr.Zero; curr = InternalNext(curr))
{ {
yield return NativeToManaged<T>(InternalDataGet(curr)); yield return NativeToManaged<T>(InternalDataGet(curr));
} }

View File

@ -5,7 +5,9 @@ using System.Runtime.InteropServices;
using System.Runtime.CompilerServices; using System.Runtime.CompilerServices;
using System.Diagnostics.Contracts; using System.Diagnostics.Contracts;
namespace Eina { // Manual wrappers around eina functions namespace Eina
{
// Manual wrappers around eina functions
public class Log public class Log
{ {
@ -55,44 +57,54 @@ public class Log
static Log() static Log()
{ {
const String name="mono"; const String name = "mono";
const String color="\033[32;1m"; const String color = "\033[32;1m";
// Maybe move this check outside when other eina stuff get support? // Maybe move this check outside when other eina stuff get support?
domain = eina_log_domain_register(name, color); domain = eina_log_domain_register(name, color);
if (domain < 0) if (domain < 0)
Console.WriteLine("Error: Couldn't register Eina log domain for name {0}.", name); {
Console.WriteLine("Error: Couldn't register Eina log domain for name {0}.", name);
}
else else
Info($"Registered mono domain with number {domain}"); {
Info($"Registered mono domain with number {domain}");
}
} }
private static void EnsureDomainRegistered() private static void EnsureDomainRegistered()
{ {
if (domain < 0) if (domain < 0)
throw new InvalidOperationException("Log domain is not registered."); {
throw new InvalidOperationException("Log domain is not registered.");
}
} }
public static void Critical(String message, [CallerLineNumber] int line=0, [CallerFilePath] string file=null, [CallerMemberName] string member = null) public static void Critical(String message, [CallerLineNumber] int line = 0, [CallerFilePath] string file = null, [CallerMemberName] string member = null)
{ {
EnsureDomainRegistered(); EnsureDomainRegistered();
eina_log_print(domain, Level.Critical, file, member, line, message); eina_log_print(domain, Level.Critical, file, member, line, message);
} }
public static void Error(String message, [CallerLineNumber] int line=0, [CallerFilePath] string file=null, [CallerMemberName] string member = null)
public static void Error(String message, [CallerLineNumber] int line = 0, [CallerFilePath] string file = null, [CallerMemberName] string member = null)
{ {
EnsureDomainRegistered(); EnsureDomainRegistered();
eina_log_print(domain, Level.Error, file, member, line, message); eina_log_print(domain, Level.Error, file, member, line, message);
} }
public static void Warning(String message, [CallerLineNumber] int line=0, [CallerFilePath] string file=null, [CallerMemberName] string member = null)
public static void Warning(String message, [CallerLineNumber] int line = 0, [CallerFilePath] string file = null, [CallerMemberName] string member = null)
{ {
EnsureDomainRegistered(); EnsureDomainRegistered();
eina_log_print(domain, Level.Warning, file, member, line, message); eina_log_print(domain, Level.Warning, file, member, line, message);
} }
public static void Info(String message, [CallerLineNumber] int line=0, [CallerFilePath] string file=null, [CallerMemberName] string member = null)
public static void Info(String message, [CallerLineNumber] int line = 0, [CallerFilePath] string file = null, [CallerMemberName] string member = null)
{ {
EnsureDomainRegistered(); EnsureDomainRegistered();
eina_log_print(domain, Level.Info, file, member, line, message); eina_log_print(domain, Level.Info, file, member, line, message);
} }
public static void Debug(String message, [CallerLineNumber] int line=0, [CallerFilePath] string file=null, [CallerMemberName] string member = null)
public static void Debug(String message, [CallerLineNumber] int line = 0, [CallerFilePath] string file = null, [CallerMemberName] string member = null)
{ {
EnsureDomainRegistered(); EnsureDomainRegistered();
eina_log_print(domain, Level.Debug, file, member, line, message); eina_log_print(domain, Level.Debug, file, member, line, message);
@ -108,4 +120,5 @@ public class Log
return eina_log_level_get(); return eina_log_level_get();
} }
} }
} }

View File

@ -6,9 +6,11 @@ using System.Linq;
using static Eina.EinaNative.PromiseNativeMethods; using static Eina.EinaNative.PromiseNativeMethods;
namespace Eina { namespace Eina
{
namespace EinaNative { namespace EinaNative
{
static internal class PromiseNativeMethods static internal class PromiseNativeMethods
{ {
@ -26,6 +28,9 @@ static internal class PromiseNativeMethods
[DllImport(efl.Libs.Eina)] [DllImport(efl.Libs.Eina)]
internal static extern void eina_promise_reject(IntPtr scheduler, Eina.Error reason); internal static extern void eina_promise_reject(IntPtr scheduler, Eina.Error reason);
[DllImport(efl.Libs.CustomExports)]
internal static extern void efl_mono_thread_safe_promise_reject(IntPtr scheduler, Eina.Error reason);
[DllImport(efl.Libs.Eina)] [DllImport(efl.Libs.Eina)]
internal static extern IntPtr eina_future_new(IntPtr promise); internal static extern IntPtr eina_future_new(IntPtr promise);
@ -80,7 +85,7 @@ public class Promise : IDisposable
/// Currently, creating a promise directly uses the Main Loop scheduler the source of notifications (i.e. the /// Currently, creating a promise directly uses the Main Loop scheduler the source of notifications (i.e. the
/// future callbacks will be called mainly from a loop iteration). /// future callbacks will be called mainly from a loop iteration).
/// </summary> /// </summary>
public Promise(CancelCb cancelCb=null) public Promise(CancelCb cancelCb = null)
{ {
Efl.Loop loop = Efl.App.AppMain; Efl.Loop loop = Efl.App.AppMain;
@ -90,10 +95,13 @@ public class Promise : IDisposable
IntPtr cb_data = IntPtr.Zero; IntPtr cb_data = IntPtr.Zero;
// A safety clean callback to mark this wrapper as invalid // A safety clean callback to mark this wrapper as invalid
CancelCb safetyCb = () => { CancelCb safetyCb = () =>
{
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (cancelCb != null) if (cancelCb != null)
{
cancelCb(); cancelCb();
}
}; };
CleanupHandle = GCHandle.Alloc(safetyCb); CleanupHandle = GCHandle.Alloc(safetyCb);
@ -105,14 +113,21 @@ public class Promise : IDisposable
private static void NativeCancelCb(IntPtr data, IntPtr dead) private static void NativeCancelCb(IntPtr data, IntPtr dead)
{ {
if (data == IntPtr.Zero) if (data == IntPtr.Zero)
{
return; return;
}
GCHandle handle = GCHandle.FromIntPtr(data); GCHandle handle = GCHandle.FromIntPtr(data);
CancelCb cb = handle.Target as CancelCb; CancelCb cb = handle.Target as CancelCb;
if (cb != null) if (cb != null)
{
cb(); cb();
}
else else
{
Eina.Log.Info("Null promise CancelCb found"); Eina.Log.Info("Null promise CancelCb found");
}
handle.Free(); handle.Free();
} }
@ -136,7 +151,14 @@ public class Promise : IDisposable
{ {
if (Handle != IntPtr.Zero) if (Handle != IntPtr.Zero)
{ {
eina_promise_reject(Handle, Eina.Error.ECANCELED); if (disposing)
{
eina_promise_reject(Handle, Eina.Error.ECANCELED);
}
else
{
efl_mono_thread_safe_promise_reject(Handle, Eina.Error.ECANCELED);
}
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
} }
} }
@ -144,7 +166,9 @@ public class Promise : IDisposable
private void SanityChecks() private void SanityChecks()
{ {
if (this.Handle == IntPtr.Zero) if (this.Handle == IntPtr.Zero)
{
throw new ObjectDisposedException(GetType().Name); throw new ObjectDisposedException(GetType().Name);
}
} }
/// <summary> /// <summary>
@ -200,7 +224,8 @@ public class Future
/// </summary> /// </summary>
public Future(IntPtr handle) public Future(IntPtr handle)
{ {
Handle = ThenRaw(handle, (Eina.Value value) => { Handle = ThenRaw(handle, (Eina.Value value) =>
{
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
return value; return value;
}); });
@ -212,12 +237,16 @@ public class Future
/// Optionally a resolved callback may be provided. If so, it will be chained /// Optionally a resolved callback may be provided. If so, it will be chained
/// before the returned future. /// before the returned future.
/// </summary> /// </summary>
public Future(Promise promise, ResolvedCb cb=null) public Future(Promise promise, ResolvedCb cb = null)
{ {
IntPtr intermediate = eina_future_new(promise.Handle); IntPtr intermediate = eina_future_new(promise.Handle);
Handle = ThenRaw(intermediate, (Eina.Value value) => { Handle = ThenRaw(intermediate, (Eina.Value value) =>
{
if (cb != null) if (cb != null)
{
value = cb(value); value = cb(value);
}
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
return value; return value;
}); });
@ -226,7 +255,9 @@ public class Future
private void SanityChecks() private void SanityChecks()
{ {
if (this.Handle == IntPtr.Zero) if (this.Handle == IntPtr.Zero)
{
throw new ObjectDisposedException(GetType().Name); throw new ObjectDisposedException(GetType().Name);
}
} }
/// <summary> /// <summary>
@ -266,14 +297,20 @@ public class Future
desc.data = GCHandle.ToIntPtr(handle); desc.data = GCHandle.ToIntPtr(handle);
return eina_future_then_from_desc(previous, desc); return eina_future_then_from_desc(previous, desc);
} }
private static Eina.ValueNative NativeResolvedCb(IntPtr data, Eina.ValueNative value, IntPtr dead_future) private static Eina.ValueNative NativeResolvedCb(IntPtr data, Eina.ValueNative value, IntPtr dead_future)
{ {
GCHandle handle = GCHandle.FromIntPtr(data); GCHandle handle = GCHandle.FromIntPtr(data);
ResolvedCb cb = handle.Target as ResolvedCb; ResolvedCb cb = handle.Target as ResolvedCb;
if (cb != null) if (cb != null)
{
value = cb(value); value = cb(value);
}
else else
{
Eina.Log.Warning("Failed to get future callback."); Eina.Log.Warning("Failed to get future callback.");
}
handle.Free(); handle.Free();
return value; return value;
} }
@ -308,14 +345,18 @@ public class Future
for (int j = 0; j <= i; j++) for (int j = 0; j <= i; j++)
{ {
if (descs[i].data == IntPtr.Zero) if (descs[i].data == IntPtr.Zero)
{
continue; continue;
}
GCHandle handle = GCHandle.FromIntPtr(descs[i].data); GCHandle handle = GCHandle.FromIntPtr(descs[i].data);
handle.Free(); handle.Free();
} }
Eina.Log.Error($"Failed to create native future description for callbacks. Error: {e.ToString()}"); Eina.Log.Error($"Failed to create native future description for callbacks. Error: {e.ToString()}");
return null; return null;
} }
return new Future(eina_future_chain_array(Handle, descs)); return new Future(eina_future_chain_array(Handle, descs));
} }
} }
@ -341,17 +382,24 @@ public class FutureMarshaler : ICustomMarshaler
{ {
Future f = managedObj as Future; Future f = managedObj as Future;
if (f == null) if (f == null)
{
return IntPtr.Zero; return IntPtr.Zero;
}
return f.Handle; return f.Handle;
} }
///<summary>Not implemented. The code receiving the native data is in charge of releasing it.</summary> ///<summary>Not implemented. The code receiving the native data is in charge of releasing it.</summary>
///<param name="pNativeData">The native pointer to be released.</param> ///<param name="pNativeData">The native pointer to be released.</param>
public void CleanUpNativeData(IntPtr pNativeData) { } public void CleanUpNativeData(IntPtr pNativeData)
{
}
///<summary>Not implemented. The runtime takes care of releasing it.</summary> ///<summary>Not implemented. The runtime takes care of releasing it.</summary>
///<param name="managedObj">The managed object to be cleaned.</param> ///<param name="managedObj">The managed object to be cleaned.</param>
public void CleanUpManagedData(object managedObj) { } public void CleanUpManagedData(object managedObj)
{
}
///<summary>Size of the native data size returned</summary> ///<summary>Size of the native data size returned</summary>
///<returns>The size of the data.</returns> ///<returns>The size of the data.</returns>
@ -363,9 +411,13 @@ public class FutureMarshaler : ICustomMarshaler
///<summary>Gets an instance of this marshaller.</summary> ///<summary>Gets an instance of this marshaller.</summary>
///<param name="cookie">A name that could be used to customize the returned marshaller. Currently not used.</param> ///<param name="cookie">A name that could be used to customize the returned marshaller. Currently not used.</param>
///<returns>The <see cref="Eina.FutureMarshaler"/> instance that will marshall the data.</returns> ///<returns>The <see cref="Eina.FutureMarshaler"/> instance that will marshall the data.</returns>
public static ICustomMarshaler GetInstance(string cookie) { public static ICustomMarshaler GetInstance(string cookie)
{
if (marshaler == null) if (marshaler == null)
{
marshaler = new FutureMarshaler(); marshaler = new FutureMarshaler();
}
return marshaler; return marshaler;
} }

View File

@ -3,7 +3,8 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Eina { namespace Eina
{
public interface ISliceBase public interface ISliceBase
{ {
@ -21,8 +22,8 @@ public struct Slice : ISliceBase
public int Length public int Length
{ {
get { return (int) Len; } get { return (int)Len; }
set { Len = (UIntPtr) value; } set { Len = (UIntPtr)value; }
} }
public Slice(IntPtr mem, UIntPtr len) public Slice(IntPtr mem, UIntPtr len)
@ -47,8 +48,8 @@ public struct RwSlice : ISliceBase
public int Length public int Length
{ {
get { return (int) Len; } get { return (int)Len; }
set { Len = (UIntPtr) value; } set { Len = (UIntPtr)value; }
} }
public RwSlice(IntPtr mem, UIntPtr len) public RwSlice(IntPtr mem, UIntPtr len)

View File

@ -5,8 +5,10 @@ using static Eina.EinaNative.StrbufNativeMethods;
namespace Eina namespace Eina
{ {
namespace EinaNative namespace EinaNative
{ {
static internal class StrbufNativeMethods static internal class StrbufNativeMethods
{ {
[DllImport(efl.Libs.Eina)] [DllImport(efl.Libs.Eina)]
@ -48,7 +50,7 @@ public class Strbuf : IDisposable
private bool Disposed; private bool Disposed;
///<summary>Creates a new Strbuf. By default its lifetime is managed.</summary> ///<summary>Creates a new Strbuf. By default its lifetime is managed.</summary>
public Strbuf(Ownership ownership=Ownership.Managed) public Strbuf(Ownership ownership = Ownership.Managed)
{ {
this.Handle = eina_strbuf_new(); this.Handle = eina_strbuf_new();
this.Ownership = ownership; this.Ownership = ownership;
@ -89,9 +91,20 @@ public class Strbuf : IDisposable
return; return;
} }
if (!Disposed && (Handle != IntPtr.Zero)) { if (!Disposed && (Handle != IntPtr.Zero))
eina_strbuf_free(Handle); {
if (disposing)
{
eina_strbuf_free(Handle);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eina_strbuf_free, Handle);
}
Handle = IntPtr.Zero;
} }
Disposed = true; Disposed = true;
} }
@ -115,7 +128,10 @@ public class Strbuf : IDisposable
public void Reset() public void Reset()
{ {
if (Disposed) if (Disposed)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
eina_strbuf_reset(Handle); eina_strbuf_reset(Handle);
} }
@ -123,7 +139,10 @@ public class Strbuf : IDisposable
public bool Append(string text) public bool Append(string text)
{ {
if (Disposed) if (Disposed)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
return eina_strbuf_append(Handle, text); return eina_strbuf_append(Handle, text);
} }
@ -131,7 +150,10 @@ public class Strbuf : IDisposable
public bool AppendEscaped(string text) public bool AppendEscaped(string text)
{ {
if (Disposed) if (Disposed)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
return eina_strbuf_append_escaped(Handle, text); return eina_strbuf_append_escaped(Handle, text);
} }
@ -139,7 +161,10 @@ public class Strbuf : IDisposable
public bool Append(char c) public bool Append(char c)
{ {
if (Disposed) if (Disposed)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
return eina_strbuf_append_char(Handle, c); return eina_strbuf_append_char(Handle, c);
} }
@ -147,10 +172,12 @@ public class Strbuf : IDisposable
public string Steal() public string Steal()
{ {
if (Disposed) if (Disposed)
{
throw new ObjectDisposedException(base.GetType().Name); throw new ObjectDisposedException(base.GetType().Name);
}
return eina_strbuf_string_steal(Handle); return eina_strbuf_string_steal(Handle);
} }
} }
} // namespace eina } // namespace eina

View File

@ -4,9 +4,11 @@ using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Eina { namespace Eina
{
public class Stringshare { public class Stringshare
{
[DllImport(efl.Libs.Eina)] public static extern System.IntPtr [DllImport(efl.Libs.Eina)] public static extern System.IntPtr
eina_stringshare_add_length(string str, System.UInt32 slen); eina_stringshare_add_length(string str, System.UInt32 slen);
[DllImport(efl.Libs.Eina)] public static extern System.IntPtr [DllImport(efl.Libs.Eina)] public static extern System.IntPtr
@ -16,4 +18,3 @@ public class Stringshare {
} }
} }

File diff suppressed because it is too large Load Diff

View File

@ -5,7 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusMessageNativeFunctions; using static eldbus.EldbusMessageNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class Timeout public static class Timeout
{ {
@ -26,6 +27,7 @@ public struct ObjectPath
{ {
return new ObjectPath(str); return new ObjectPath(str);
} }
public static implicit operator string(ObjectPath path) public static implicit operator string(ObjectPath path)
{ {
return path.value; return path.value;
@ -46,6 +48,7 @@ public struct SignatureString
{ {
return new SignatureString(str); return new SignatureString(str);
} }
public static implicit operator string(SignatureString sig) public static implicit operator string(SignatureString sig)
{ {
return sig.value; return sig.value;
@ -66,6 +69,7 @@ public struct UnixFd
{ {
return new UnixFd(fd); return new UnixFd(fd);
} }
public static implicit operator Int32(UnixFd unix_fd) public static implicit operator Int32(UnixFd unix_fd)
{ {
return unix_fd.value; return unix_fd.value;
@ -75,23 +79,107 @@ public struct UnixFd
public static class Argument public static class Argument
{ {
public class ByteType { public const char Code = 'y'; public const string Signature = "y"; } public class ByteType
public class BooleanType { public const char Code = 'b'; public const string Signature = "b"; } {
public class Int16Type { public const char Code = 'n'; public const string Signature = "n"; } public const char Code = 'y';
public class UInt16Type { public const char Code = 'q'; public const string Signature = "q"; } public const string Signature = "y";
public class Int32Type { public const char Code = 'i'; public const string Signature = "i"; } }
public class UInt32Type { public const char Code = 'u'; public const string Signature = "u"; }
public class Int64Type { public const char Code = 'x'; public const string Signature = "x"; } public class BooleanType
public class UInt64Type { public const char Code = 't'; public const string Signature = "t"; } {
public class DoubleType { public const char Code = 'd'; public const string Signature = "d"; } public const char Code = 'b';
public class StringType { public const char Code = 's'; public const string Signature = "s"; } public const string Signature = "b";
public class ObjectPathType { public const char Code = 'o'; public const string Signature = "o"; } }
public class SignatureType { public const char Code = 'g'; public const string Signature = "g"; }
public class ArrayType { public const char Code = 'a'; public const string Signature = "a"; } public class Int16Type
public class StructType { public const char Code = 'r'; public const string Signature = "r"; } {
public class VariantType { public const char Code = 'v'; public const string Signature = "v"; } public const char Code = 'n';
public class DictEntryType { public const char Code = 'e'; public const string Signature = "e"; } public const string Signature = "n";
public class UnixFdType { public const char Code = 'h'; public const string Signature = "h"; } }
public class UInt16Type
{
public const char Code = 'q';
public const string Signature = "q";
}
public class Int32Type
{
public const char Code = 'i';
public const string Signature = "i";
}
public class UInt32Type
{
public const char Code = 'u';
public const string Signature = "u";
}
public class Int64Type
{
public const char Code = 'x';
public const string Signature = "x";
}
public class UInt64Type
{
public const char Code = 't';
public const string Signature = "t";
}
public class DoubleType
{
public const char Code = 'd';
public const string Signature = "d";
}
public class StringType
{
public const char Code = 's';
public const string Signature = "s";
}
public class ObjectPathType
{
public const char Code = 'o';
public const string Signature = "o";
}
public class SignatureType
{
public const char Code = 'g';
public const string Signature = "g";
}
public class ArrayType
{
public const char Code = 'a';
public const string Signature = "a";
}
public class StructType
{
public const char Code = 'r';
public const string Signature = "r";
}
public class VariantType
{
public const char Code = 'v';
public const string Signature = "v";
}
public class DictEntryType
{
public const char Code = 'e';
public const string Signature = "e";
}
public class UnixFdType
{
public const char Code = 'h';
public const string Signature = "h";
}
// public static readonly ByteType ByteT = new ByteType(); // public static readonly ByteType ByteT = new ByteType();
// public static readonly BooleanType BooleanT = new BooleanType(); // public static readonly BooleanType BooleanT = new BooleanType();
@ -135,13 +223,17 @@ public abstract class BasicMessageArgument
public void AppendTo(eldbus.Message msg) public void AppendTo(eldbus.Message msg)
{ {
if (!InternalAppendTo(msg)) if (!InternalAppendTo(msg))
{
throw new SEHException("Eldbus: could not append basic type to eldbus.Message"); throw new SEHException("Eldbus: could not append basic type to eldbus.Message");
}
} }
public void AppendTo(eldbus.MessageIterator iter) public void AppendTo(eldbus.MessageIterator iter)
{ {
if (!InternalAppendTo(iter)) if (!InternalAppendTo(iter))
{
throw new SEHException("Eldbus: could not append basic type to eldbus.MessageIterator"); throw new SEHException("Eldbus: could not append basic type to eldbus.MessageIterator");
}
} }
public abstract char TypeCode {get;} public abstract char TypeCode {get;}
@ -219,8 +311,15 @@ public class ByteMessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.ByteType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.ByteType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -242,8 +341,15 @@ public class BoolMessageArgument : BasicMessageArgument
value = Convert.ToInt32(arg); value = Convert.ToInt32(arg);
} }
public override char TypeCode { get { return Argument.BooleanType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.BooleanType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -265,8 +371,15 @@ public class Int16MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.Int16Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.Int16Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -288,8 +401,15 @@ public class UInt16MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.UInt16Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.UInt16Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -311,8 +431,15 @@ public class Int32MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.Int32Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.Int32Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -334,8 +461,15 @@ public class UInt32MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.UInt32Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.UInt32Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -357,8 +491,15 @@ public class Int64MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.Int64Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.Int64Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -380,8 +521,15 @@ public class UInt64MessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.UInt64Type.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.UInt64Type.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -403,8 +551,15 @@ public class DoubleMessageArgument : BasicMessageArgument
value = arg; value = arg;
} }
public override char TypeCode { get { return Argument.DoubleType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.DoubleType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -439,32 +594,53 @@ public abstract class StringLikeMessageArgument : BasicMessageArgument
public class StringMessageArgument : StringLikeMessageArgument public class StringMessageArgument : StringLikeMessageArgument
{ {
public StringMessageArgument(string arg) public StringMessageArgument(string arg) : base(arg)
: base(arg) {
{} }
public override char TypeCode { get { return Argument.StringType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.StringType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
} }
public class ObjectPathMessageArgument : StringLikeMessageArgument public class ObjectPathMessageArgument : StringLikeMessageArgument
{ {
public ObjectPathMessageArgument(ObjectPath arg) public ObjectPathMessageArgument(ObjectPath arg) : base(arg.value)
: base(arg.value) {
{} }
public override char TypeCode { get { return Argument.ObjectPathType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.ObjectPathType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
} }
public class SignatureMessageArgument : StringLikeMessageArgument public class SignatureMessageArgument : StringLikeMessageArgument
{ {
public SignatureMessageArgument(SignatureString arg) public SignatureMessageArgument(SignatureString arg) : base(arg.value)
: base(arg.value) {
{} }
public override char TypeCode { get { return Argument.SignatureType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.SignatureType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
} }
public class UnixFdMessageArgument : BasicMessageArgument public class UnixFdMessageArgument : BasicMessageArgument
@ -476,8 +652,15 @@ public class UnixFdMessageArgument : BasicMessageArgument
value = arg.value; value = arg.value;
} }
public override char TypeCode { get { return Argument.UnixFdType.Code; } } public override char TypeCode
public override string Signature { get { return Argument.ByteType.Signature; } } {
get { return Argument.UnixFdType.Code; }
}
public override string Signature
{
get { return Argument.ByteType.Signature; }
}
protected override bool InternalAppendTo(eldbus.Message msg) protected override bool InternalAppendTo(eldbus.Message msg)
{ {
@ -497,7 +680,10 @@ public static class Common
public static void RaiseNullHandle() public static void RaiseNullHandle()
{ {
if (NullHandleError == 0) if (NullHandleError == 0)
{
NullHandleError = Eina.Error.Register("Eldbus: null handle"); NullHandleError = Eina.Error.Register("Eldbus: null handle");
}
Eina.Error.Raise(NullHandleError); Eina.Error.Raise(NullHandleError);
} }
@ -511,7 +697,10 @@ public static class Common
public static Eldbus_Message_Cb GetMessageCbWrapper() public static Eldbus_Message_Cb GetMessageCbWrapper()
{ {
if (message_cb_wrapper == null) if (message_cb_wrapper == null)
{
message_cb_wrapper = new Eldbus_Message_Cb(MessageCbWrapper); message_cb_wrapper = new Eldbus_Message_Cb(MessageCbWrapper);
}
return message_cb_wrapper; return message_cb_wrapper;
} }
@ -532,7 +721,7 @@ public static class Common
msg = new eldbus.Message(msg_hdl, false); msg = new eldbus.Message(msg_hdl, false);
pending = new eldbus.Pending(pending_hdl, false); pending = new eldbus.Pending(pending_hdl, false);
} }
catch(Exception e) catch (Exception e)
{ {
Eina.Log.Error("Eldbus: could not convert Eldbus_Message_Cb parameters. Exception: " + e.ToString()); Eina.Log.Error("Eldbus: could not convert Eldbus_Message_Cb parameters. Exception: " + e.ToString());
return; return;
@ -542,7 +731,7 @@ public static class Common
{ {
dlgt(msg, pending); dlgt(msg, pending);
} }
catch(Exception e) catch (Exception e)
{ {
Eina.Log.Error("Eldbus: Eldbus_Message_Cb delegate error. Exception: " + e.ToString()); Eina.Log.Error("Eldbus: Eldbus_Message_Cb delegate error. Exception: " + e.ToString());
} }
@ -553,5 +742,3 @@ public static class Common
} }
} }

View File

@ -3,7 +3,8 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace eldbus { namespace eldbus
{
public static class Config public static class Config
{ {
@ -13,7 +14,9 @@ public static class Config
public static void Init() public static void Init()
{ {
if (eldbus_init() == 0) if (eldbus_init() == 0)
{
throw new Efl.EflException("Failed to initialize Eldbus"); throw new Efl.EflException("Failed to initialize Eldbus");
}
} }
public static void Shutdown() public static void Shutdown()

View File

@ -5,8 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusConnectionNativeFunctions; using static eldbus.EldbusConnectionNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class EldbusConnectionNativeFunctions public static class EldbusConnectionNativeFunctions
{ {
@ -155,10 +155,21 @@ public class Connection : IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (Own) if (Own)
eldbus_connection_unref(h); {
if (disposing)
{
eldbus_connection_unref(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eldbus_connection_unref, h);
}
}
} }
public void Dispose() public void Dispose()
@ -184,15 +195,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (msg == null) if (msg == null)
{
throw new ArgumentNullException("msg"); throw new ArgumentNullException("msg");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_connection_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout); var pending_hdl = eldbus_connection_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_connection_send"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_connection_send");
}
msg.Ref(); msg.Ref();
@ -204,7 +219,10 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_connection_unique_name_get(Handle); var ptr = eldbus_connection_unique_name_get(Handle);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
return null; return null;
}
return Eina.StringConversion.NativeUtf8ToManagedString(ptr); return Eina.StringConversion.NativeUtf8ToManagedString(ptr);
} }
@ -213,15 +231,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (bus == null) if (bus == null)
{
throw new ArgumentNullException("bus"); throw new ArgumentNullException("bus");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_name_request(Handle, bus, flags, cb_wrapper, cb_data); var pending_hdl = eldbus_name_request(Handle, bus, flags, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_request"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_request");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -231,15 +253,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (bus == null) if (bus == null)
{
throw new ArgumentNullException("bus"); throw new ArgumentNullException("bus");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_name_release(Handle, bus, cb_wrapper, cb_data); var pending_hdl = eldbus_name_release(Handle, bus, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_release"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_release");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -249,15 +275,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (bus == null) if (bus == null)
{
throw new ArgumentNullException("bus"); throw new ArgumentNullException("bus");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_name_owner_get(Handle, bus, cb_wrapper, cb_data); var pending_hdl = eldbus_name_owner_get(Handle, bus, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_owner_get"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_owner_get");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -267,15 +297,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (bus == null) if (bus == null)
{
throw new ArgumentNullException("bus"); throw new ArgumentNullException("bus");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_name_owner_has(Handle, bus, cb_wrapper, cb_data); var pending_hdl = eldbus_name_owner_has(Handle, bus, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_owner_has"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_owner_has");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -289,8 +323,10 @@ public class Connection : IDisposable
var pending_hdl = eldbus_names_list(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_names_list(Handle, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_names_list"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_names_list");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -304,8 +340,10 @@ public class Connection : IDisposable
var pending_hdl = eldbus_names_activatable_list(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_names_activatable_list(Handle, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_names_activatable_list"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_names_activatable_list");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -319,8 +357,10 @@ public class Connection : IDisposable
var pending_hdl = eldbus_hello(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_hello(Handle, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_hello"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_hello");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -330,15 +370,19 @@ public class Connection : IDisposable
CheckHandle(); CheckHandle();
if (bus == null) if (bus == null)
{
throw new ArgumentNullException("bus"); throw new ArgumentNullException("bus");
}
IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr()); IntPtr cb_wrapper = (dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr());
IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt)); IntPtr cb_data = (dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt));
var pending_hdl = eldbus_name_start(Handle, bus, flags, cb_wrapper, cb_data); var pending_hdl = eldbus_name_start(Handle, bus, flags, cb_wrapper, cb_data);
if(pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_start"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_name_start");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }

View File

@ -5,7 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusMessageNativeFunctions; using static eldbus.EldbusMessageNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class EldbusMessageNativeFunctions public static class EldbusMessageNativeFunctions
{ {
@ -223,10 +224,21 @@ public class Message : IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (Own) if (Own)
eldbus_message_unref(h); {
if (disposing)
{
eldbus_message_unref(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eldbus_message_unref, h);
}
}
} }
public void Dispose() public void Dispose()
@ -251,7 +263,10 @@ public class Message : IDisposable
{ {
var ptr = eldbus_message_method_call_new(dest, path, iface, method); var ptr = eldbus_message_method_call_new(dest, path, iface, method);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_method_call_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_method_call_new");
}
return new eldbus.Message(ptr, true); return new eldbus.Message(ptr, true);
} }
@ -259,7 +274,10 @@ public class Message : IDisposable
{ {
var ptr = eldbus_message_signal_new(path, _interface, name); var ptr = eldbus_message_signal_new(path, _interface, name);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_signal_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_signal_new");
}
return new eldbus.Message(ptr, true); return new eldbus.Message(ptr, true);
} }
@ -322,7 +340,10 @@ public class Message : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_message_error_new(Handle, error_name, error_msg); var ptr = eldbus_message_error_new(Handle, error_name, error_msg);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_error_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_error_new");
}
return new eldbus.Message(ptr, false); return new eldbus.Message(ptr, false);
} }
@ -331,7 +352,10 @@ public class Message : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_message_method_return_new(Handle); var ptr = eldbus_message_method_return_new(Handle);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_method_return_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_message_method_return_new");
}
return new eldbus.Message(ptr, false); return new eldbus.Message(ptr, false);
} }
@ -459,7 +483,10 @@ public class Message : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_message_iter_get(Handle); var ptr = eldbus_message_iter_get(Handle);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_get"); throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_get");
}
return new eldbus.MessageIterator(ptr, IntPtr.Zero); return new eldbus.MessageIterator(ptr, IntPtr.Zero);
} }
} }
@ -514,12 +541,18 @@ public class MessageIterator
IntPtr new_iter = IntPtr.Zero; IntPtr new_iter = IntPtr.Zero;
if (signature[0] == 'v') if (signature[0] == 'v')
{
new_iter = eldbus_message_iter_container_new(Handle, 'v', signature.Substring(1)); new_iter = eldbus_message_iter_container_new(Handle, 'v', signature.Substring(1));
}
else if (!eldbus_message_iter_arguments_append(Handle, signature, out new_iter)) else if (!eldbus_message_iter_arguments_append(Handle, signature, out new_iter))
{
throw new SEHException("Eldbus: could not append container type"); throw new SEHException("Eldbus: could not append container type");
}
if (new_iter == IntPtr.Zero) if (new_iter == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_arguments_append"); throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_arguments_append");
}
return new eldbus.MessageIterator(new_iter, Handle); return new eldbus.MessageIterator(new_iter, Handle);
} }
@ -531,7 +564,9 @@ public class MessageIterator
IntPtr new_iter = eldbus_message_iter_container_new(Handle, type, contained_signature); IntPtr new_iter = eldbus_message_iter_container_new(Handle, type, contained_signature);
if (new_iter == IntPtr.Zero) if (new_iter == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_container_new"); throw new SEHException("Eldbus: could not get `MessageIterator' object from eldbus_message_iter_container_new");
}
return new eldbus.MessageIterator(new_iter, Handle); return new eldbus.MessageIterator(new_iter, Handle);
} }
@ -541,10 +576,14 @@ public class MessageIterator
CheckHandle(); CheckHandle();
if (Parent == IntPtr.Zero) if (Parent == IntPtr.Zero)
{
throw new SEHException("Eldbus: can not close MessageIterator open container without a parent"); throw new SEHException("Eldbus: can not close MessageIterator open container without a parent");
}
if (!eldbus_message_iter_container_close(Parent, Handle)) if (!eldbus_message_iter_container_close(Parent, Handle))
{
throw new SEHException("Eldbus: could not close MessageIterator"); throw new SEHException("Eldbus: could not close MessageIterator");
}
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
Parent = IntPtr.Zero; Parent = IntPtr.Zero;
@ -654,7 +693,10 @@ public class MessageIterator
IntPtr hdl = IntPtr.Zero; IntPtr hdl = IntPtr.Zero;
bool r = eldbus_message_iter_get_and_next(Handle, typecode, out hdl); bool r = eldbus_message_iter_get_and_next(Handle, typecode, out hdl);
if (hdl == IntPtr.Zero) if (hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get argument"); throw new SEHException("Eldbus: could not get argument");
}
iter = new eldbus.MessageIterator(hdl, Handle); iter = new eldbus.MessageIterator(hdl, Handle);
return r; return r;
@ -665,7 +707,10 @@ public class MessageIterator
CheckHandle(); CheckHandle();
IntPtr hdl = IntPtr.Zero; IntPtr hdl = IntPtr.Zero;
if (!eldbus_message_iter_arguments_get(Handle, signatue, out hdl) || hdl == IntPtr.Zero) if (!eldbus_message_iter_arguments_get(Handle, signatue, out hdl) || hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get argument"); throw new SEHException("Eldbus: could not get argument");
}
iter = new eldbus.MessageIterator(hdl, Handle); iter = new eldbus.MessageIterator(hdl, Handle);
return Next(); return Next();
@ -764,7 +809,10 @@ public class MessageIterator
CheckHandle(); CheckHandle();
IntPtr hdl = IntPtr.Zero; IntPtr hdl = IntPtr.Zero;
if (!eldbus_message_iter_arguments_get(Handle, signatue, out hdl) || hdl == IntPtr.Zero) if (!eldbus_message_iter_arguments_get(Handle, signatue, out hdl) || hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get argument"); throw new SEHException("Eldbus: could not get argument");
}
iter = new eldbus.MessageIterator(hdl, Handle); iter = new eldbus.MessageIterator(hdl, Handle);
} }
@ -789,7 +837,9 @@ public class MessageIterator
CheckHandle(); CheckHandle();
if (!eldbus_message_iter_fixed_array_get(Handle, type_code, out value, out n_elements)) if (!eldbus_message_iter_fixed_array_get(Handle, type_code, out value, out n_elements))
{
throw new SEHException("Eldbus: could not get fixed array"); throw new SEHException("Eldbus: could not get fixed array");
}
} }
public void GetFixedArray(out byte[] array) public void GetFixedArray(out byte[] array)
@ -880,4 +930,3 @@ public class MessageIterator
} }
} }

View File

@ -7,8 +7,8 @@ using static eldbus.EldbusObjectNativeFunctions;
using IntPtr = System.IntPtr; using IntPtr = System.IntPtr;
namespace eldbus { namespace eldbus
{
public static class EldbusObjectNativeFunctions public static class EldbusObjectNativeFunctions
{ {
@ -112,16 +112,26 @@ public class Object : System.IDisposable
public Object(eldbus.Connection conn, string bus, string path) public Object(eldbus.Connection conn, string bus, string path)
{ {
if (conn == null) if (conn == null)
{
throw new System.ArgumentNullException("conn"); throw new System.ArgumentNullException("conn");
}
if (bus == null) if (bus == null)
{
throw new System.ArgumentNullException("bus"); throw new System.ArgumentNullException("bus");
}
if (path == null) if (path == null)
{
throw new System.ArgumentNullException("path"); throw new System.ArgumentNullException("path");
}
var handle = eldbus_object_get(conn.Handle, bus, path); var handle = eldbus_object_get(conn.Handle, bus, path);
if (handle == IntPtr.Zero) if (handle == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Object' object from eldbus_object_get"); throw new SEHException("Eldbus: could not get `Object' object from eldbus_object_get");
}
InitNew(handle, true); InitNew(handle, true);
} }
@ -136,10 +146,21 @@ public class Object : System.IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (Own) if (Own)
eldbus_object_unref(h); {
if (disposing)
{
eldbus_object_unref(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eldbus_object_unref, h);
}
}
} }
public void Dispose() public void Dispose()
@ -166,7 +187,9 @@ public class Object : System.IDisposable
var conn = eldbus_object_connection_get(Handle); var conn = eldbus_object_connection_get(Handle);
if (conn == IntPtr.Zero) if (conn == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Connection' object from eldbus_object_connection_get"); throw new SEHException("Eldbus: could not get `Connection' object from eldbus_object_connection_get");
}
return new eldbus.Connection(conn, false); return new eldbus.Connection(conn, false);
} }
@ -202,7 +225,9 @@ public class Object : System.IDisposable
CheckHandle(); CheckHandle();
if (msg == null) if (msg == null)
{
throw new System.ArgumentNullException("msg"); throw new System.ArgumentNullException("msg");
}
IntPtr cb_wrapper = dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr(); IntPtr cb_wrapper = dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr();
IntPtr cb_data = dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt); IntPtr cb_data = dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt);
@ -210,7 +235,9 @@ public class Object : System.IDisposable
var pending_hdl = eldbus_object_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout); var pending_hdl = eldbus_object_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_send"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_send");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -222,7 +249,9 @@ public class Object : System.IDisposable
var hdl = eldbus_object_method_call_new(Handle, _interface, member); var hdl = eldbus_object_method_call_new(Handle, _interface, member);
if (hdl == IntPtr.Zero) if (hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_object_method_call_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_object_method_call_new");
}
return new eldbus.Message(hdl, false); return new eldbus.Message(hdl, false);
} }
@ -237,7 +266,9 @@ public class Object : System.IDisposable
var pending_hdl = eldbus_object_peer_ping(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_object_peer_ping(Handle, cb_wrapper, cb_data);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_peer_ping"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_peer_ping");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -252,7 +283,9 @@ public class Object : System.IDisposable
var pending_hdl = eldbus_object_peer_machine_id_get(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_object_peer_machine_id_get(Handle, cb_wrapper, cb_data);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_peer_machine_id_get"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_peer_machine_id_get");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -267,7 +300,9 @@ public class Object : System.IDisposable
var pending_hdl = eldbus_object_introspect(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_object_introspect(Handle, cb_wrapper, cb_data);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_introspect"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_introspect");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -282,12 +317,12 @@ public class Object : System.IDisposable
var pending_hdl = eldbus_object_managed_objects_get(Handle, cb_wrapper, cb_data); var pending_hdl = eldbus_object_managed_objects_get(Handle, cb_wrapper, cb_data);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_managed_objects_get"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_object_managed_objects_get");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
} }
} }

View File

@ -5,7 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusPendingNativeFunctions; using static eldbus.EldbusPendingNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class EldbusPendingNativeFunctions public static class EldbusPendingNativeFunctions
{ {
@ -108,4 +109,3 @@ public class Pending
} }
} }

View File

@ -5,7 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusProxyNativeFunctions; using static eldbus.EldbusProxyNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class EldbusProxyNativeFunctions public static class EldbusProxyNativeFunctions
{ {
@ -104,10 +105,21 @@ public class Proxy : IDisposable
IntPtr h = Handle; IntPtr h = Handle;
Handle = IntPtr.Zero; Handle = IntPtr.Zero;
if (h == IntPtr.Zero) if (h == IntPtr.Zero)
{
return; return;
}
if (Own) if (Own)
eldbus_proxy_unref(h); {
if (disposing)
{
eldbus_proxy_unref(h);
}
else
{
Efl.Eo.Globals.efl_mono_thread_safe_free_cb_exec(eldbus_proxy_unref, h);
}
}
} }
public void Dispose() public void Dispose()
@ -133,7 +145,10 @@ public class Proxy : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_proxy_object_get(Handle); var ptr = eldbus_proxy_object_get(Handle);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Object' object from eldbus_proxy_object_get"); throw new SEHException("Eldbus: could not get `Object' object from eldbus_proxy_object_get");
}
return new eldbus.Object(ptr, false); return new eldbus.Object(ptr, false);
} }
@ -149,11 +164,16 @@ public class Proxy : IDisposable
CheckHandle(); CheckHandle();
if (member == null) if (member == null)
{
throw new ArgumentNullException("member"); throw new ArgumentNullException("member");
}
var ptr = eldbus_proxy_method_call_new(Handle, member); var ptr = eldbus_proxy_method_call_new(Handle, member);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_proxy_method_call_new"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_proxy_method_call_new");
}
return new eldbus.Message(ptr, false); return new eldbus.Message(ptr, false);
} }
@ -162,7 +182,9 @@ public class Proxy : IDisposable
CheckHandle(); CheckHandle();
if (msg == null) if (msg == null)
{
throw new ArgumentNullException("msg"); throw new ArgumentNullException("msg");
}
IntPtr cb_wrapper = dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr(); IntPtr cb_wrapper = dlgt == null ? IntPtr.Zero : eldbus.Common.GetMessageCbWrapperPtr();
IntPtr cb_data = dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt); IntPtr cb_data = dlgt == null ? IntPtr.Zero : Marshal.GetFunctionPointerForDelegate(dlgt);
@ -170,7 +192,9 @@ public class Proxy : IDisposable
var pending_hdl = eldbus_proxy_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout); var pending_hdl = eldbus_proxy_send(Handle, msg.Handle, cb_wrapper, cb_data, timeout);
if (pending_hdl == IntPtr.Zero) if (pending_hdl == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Pending' object from eldbus_proxy_send"); throw new SEHException("Eldbus: could not get `Pending' object from eldbus_proxy_send");
}
return new eldbus.Pending(pending_hdl, false); return new eldbus.Pending(pending_hdl, false);
} }
@ -180,7 +204,10 @@ public class Proxy : IDisposable
CheckHandle(); CheckHandle();
var ptr = eldbus_proxy_send_and_block(Handle, msg.Handle, timeout); var ptr = eldbus_proxy_send_and_block(Handle, msg.Handle, timeout);
if (ptr == IntPtr.Zero) if (ptr == IntPtr.Zero)
{
throw new SEHException("Eldbus: could not get `Message' object from eldbus_proxy_send_and_block"); throw new SEHException("Eldbus: could not get `Message' object from eldbus_proxy_send_and_block");
}
return new eldbus.Message(ptr, true); return new eldbus.Message(ptr, true);
} }
@ -205,4 +232,3 @@ public class Proxy : IDisposable
} }
} }

View File

@ -5,7 +5,8 @@ using System.Runtime.InteropServices;
using static eldbus.EldbusServiceNativeFunctions; using static eldbus.EldbusServiceNativeFunctions;
namespace eldbus { namespace eldbus
{
public static class EldbusServiceNativeFunctions public static class EldbusServiceNativeFunctions
{ {
@ -65,4 +66,3 @@ public static class EldbusServiceNativeFunctions
} }
} }

View File

@ -1,7 +1,11 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
///<summary>Class to load functions pointers from a native module. ///<summary>Class to load functions pointers from a native module.
/// ///
@ -51,14 +55,20 @@ public class FunctionWrapper<T> // NOTE: When supporting C# >=7.3, add a where T
private static FunctionLoadResult<T> LazyInitialization(NativeModule module, string functionName) private static FunctionLoadResult<T> LazyInitialization(NativeModule module, string functionName)
{ {
if (module.Module == IntPtr.Zero) if (module.Module == IntPtr.Zero)
{
return new FunctionLoadResult<T>(FunctionLoadResultKind.LibraryNotFound); return new FunctionLoadResult<T>(FunctionLoadResultKind.LibraryNotFound);
}
else else
{ {
IntPtr funcptr = FunctionInterop.LoadFunctionPointer(module.Module, functionName); IntPtr funcptr = FunctionInterop.LoadFunctionPointer(module.Module, functionName);
if (funcptr == IntPtr.Zero) if (funcptr == IntPtr.Zero)
{
return new FunctionLoadResult<T>(FunctionLoadResultKind.FunctionNotFound); return new FunctionLoadResult<T>(FunctionLoadResultKind.FunctionNotFound);
}
else else
{
return new FunctionLoadResult<T>(Marshal.GetDelegateForFunctionPointer<T>(funcptr)); return new FunctionLoadResult<T>(Marshal.GetDelegateForFunctionPointer<T>(funcptr));
}
} }
} }
@ -66,7 +76,7 @@ public class FunctionWrapper<T> // NOTE: When supporting C# >=7.3, add a where T
///<param name="moduleName">The name of the module containing the function.</param> ///<param name="moduleName">The name of the module containing the function.</param>
///<param name="functionName">The name of the function to search for.</param> ///<param name="functionName">The name of the function to search for.</param>
public FunctionWrapper(string moduleName, string functionName) public FunctionWrapper(string moduleName, string functionName)
: this (new NativeModule(moduleName), functionName) : this(new NativeModule(moduleName), functionName)
{ {
} }
@ -95,7 +105,8 @@ public class FunctionWrapper<T> // NOTE: When supporting C# >=7.3, add a where T
} }
///<summary>The outcome of the function load process.</summary> ///<summary>The outcome of the function load process.</summary>
public enum FunctionLoadResultKind { public enum FunctionLoadResultKind
{
///<summary>Function was loaded successfully.</summary> ///<summary>Function was loaded successfully.</summary>
Success, Success,
///<summary>Library was not found.</summary> ///<summary>Library was not found.</summary>
@ -116,9 +127,13 @@ public class FunctionLoadResult<T>
///Throws InvalidOperationException if trying to access while not loaded.</summary> ///Throws InvalidOperationException if trying to access while not loaded.</summary>
public T Delegate public T Delegate
{ {
get { get
{
if (_Delegate == null) if (_Delegate == null)
{
throw new InvalidOperationException($"Trying to get Delegate while not loaded. Load result: {Kind}"); throw new InvalidOperationException($"Trying to get Delegate while not loaded. Load result: {Kind}");
}
return _Delegate; return _Delegate;
} }
} }
@ -139,4 +154,6 @@ public class FunctionLoadResult<T>
} }
} }
} } }
}

View File

@ -1,7 +1,11 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
public partial class FunctionInterop public partial class FunctionInterop
{ {
@ -21,4 +25,6 @@ public partial class FunctionInterop
} }
} }
} } }
}

View File

@ -1,7 +1,11 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
public partial class FunctionInterop public partial class FunctionInterop
{ {
@ -12,4 +16,6 @@ public partial class FunctionInterop
=> FunctionInterop.GetProcAddress(nativeLibraryHandle, functionName); => FunctionInterop.GetProcAddress(nativeLibraryHandle, functionName);
} }
} } }
}

View File

@ -1,6 +1,10 @@
using System; using System;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
///<summary>Wraps a native module that was opened with dlopen/LoadLibrary.</summary> ///<summary>Wraps a native module that was opened with dlopen/LoadLibrary.</summary>
public partial class NativeModule : IDisposable public partial class NativeModule : IDisposable
@ -35,4 +39,6 @@ public partial class NativeModule : IDisposable
} }
} }
} } }
}

View File

@ -1,7 +1,11 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
public partial class NativeModule public partial class NativeModule
{ {
@ -60,11 +64,11 @@ public partial class NativeModule
} }
} }
} }
return r; return r;
} }
} }
}
}
} }

View File

@ -1,7 +1,11 @@
using System; using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace Efl { namespace Eo { namespace Efl
{
namespace Eo
{
public class partial NativeModule public class partial NativeModule
{ {
@ -9,7 +13,6 @@ public class partial NativeModule
public static extern IntPtr LoadLibrary(string libFilename); public static extern IntPtr LoadLibrary(string libFilename);
} }
}
}
} }

File diff suppressed because it is too large Load Diff

View File

@ -51,28 +51,35 @@ public struct EolianPD
} }
#pragma warning disable 0169 #pragma warning disable 0169
public struct EvasObjectBoxLayout public struct EvasObjectBoxLayout
{ {
IntPtr o; IntPtr o;
IntPtr priv; IntPtr priv;
IntPtr user_data; IntPtr user_data;
}; };
[StructLayout(LayoutKind.Sequential, CharSet=CharSet.Ansi)] [StructLayout(LayoutKind.Sequential, CharSet=CharSet.Ansi)]
public struct EvasObjectBoxData public struct EvasObjectBoxData
{ {
} }
public struct EvasObjectBoxOption {
public struct EvasObjectBoxOption
{
IntPtr obj; IntPtr obj;
[MarshalAsAttribute(UnmanagedType.U1)] bool max_reached; [MarshalAsAttribute(UnmanagedType.U1)] bool max_reached;
[MarshalAsAttribute(UnmanagedType.U1)] bool min_reached; [MarshalAsAttribute(UnmanagedType.U1)] bool min_reached;
Evas.Coord alloc_size; Evas.Coord alloc_size;
}; };
#pragma warning restore 0169 #pragma warning restore 0169
namespace Efl { namespace Efl
{
[StructLayout(LayoutKind.Sequential)] [StructLayout(LayoutKind.Sequential)]
public struct EventDescription { public struct EventDescription
{
public IntPtr Name; public IntPtr Name;
[MarshalAs(UnmanagedType.U1)] public bool Unfreezable; [MarshalAs(UnmanagedType.U1)] public bool Unfreezable;
[MarshalAs(UnmanagedType.U1)] public bool Legacy_is; [MarshalAs(UnmanagedType.U1)] public bool Legacy_is;
@ -94,20 +101,26 @@ public struct EventDescription {
{ {
IntPtr data = Efl.Eo.FunctionInterop.LoadFunctionPointer(module, name); IntPtr data = Efl.Eo.FunctionInterop.LoadFunctionPointer(module, name);
if (data == IntPtr.Zero) { if (data == IntPtr.Zero)
{
string error = Eina.StringConversion.NativeUtf8ToManagedString(Efl.Eo.Globals.dlerror()); string error = Eina.StringConversion.NativeUtf8ToManagedString(Efl.Eo.Globals.dlerror());
throw new Exception(error); throw new Exception(error);
} }
descriptions.Add(name, data); descriptions.Add(name, data);
} }
return descriptions[name]; return descriptions[name];
} }
}; };
public delegate void EventCb(System.IntPtr data, ref Event.NativeStruct evt); public delegate void EventCb(System.IntPtr data, ref Event.NativeStruct evt);
public delegate void FreeGCHandleCb(System.IntPtr gcHandle);
public delegate void RemoveEventsCb(System.IntPtr obj, System.IntPtr gcHandle);
[StructLayout(LayoutKind.Sequential)] [StructLayout(LayoutKind.Sequential)]
public struct TextCursorCursor { public struct TextCursorCursor
{
IntPtr obj; IntPtr obj;
UIntPtr pos; // UIntPtr to automatically change size_t between 32/64 UIntPtr pos; // UIntPtr to automatically change size_t between 32/64
IntPtr node; IntPtr node;
@ -115,7 +128,8 @@ public struct TextCursorCursor {
} }
[StructLayout(LayoutKind.Sequential)] [StructLayout(LayoutKind.Sequential)]
public struct TextAnnotateAnnotation { public struct TextAnnotateAnnotation
{
IntPtr list; IntPtr list;
IntPtr obj; IntPtr obj;
IntPtr start_node; IntPtr start_node;
@ -125,9 +139,11 @@ public struct TextAnnotateAnnotation {
public delegate void SignalCb(IntPtr data, IntPtr obj, IntPtr emission, IntPtr source); public delegate void SignalCb(IntPtr data, IntPtr obj, IntPtr emission, IntPtr source);
namespace Access { namespace Access
{
public struct ActionData { public struct ActionData
{
public IntPtr name; public IntPtr name;
public IntPtr action; public IntPtr action;
public IntPtr param; public IntPtr param;
@ -138,16 +154,25 @@ public struct ActionData {
} // namespace Efl } // namespace Efl
namespace Evas { namespace Evas
{
public struct Coord { public struct Coord
{
int val; int val;
public Coord(int value) { val = value; } public Coord(int value)
static public implicit operator Coord(int val) { {
val = value;
}
static public implicit operator Coord(int val)
{
return new Coord(val); return new Coord(val);
} }
static public implicit operator int(Coord coord) {
static public implicit operator int(Coord coord)
{
return coord.val; return coord.val;
} }
} }
@ -155,44 +180,44 @@ public struct Coord {
/* Copied from Evas_Legacy.h */ /* Copied from Evas_Legacy.h */
public enum TextStyleType public enum TextStyleType
{ {
///<summary> plain, standard text.</summary> ///<summary> plain, standard text.</summary>
Plain = 0, Plain = 0,
///<summary> text with shadow underneath.</summary> ///<summary> text with shadow underneath.</summary>
Shadow, Shadow,
///<summary> text with an outline.</summary> ///<summary> text with an outline.</summary>
Outline, Outline,
///<summary> text with a soft outline.</summary> ///<summary> text with a soft outline.</summary>
SoftOutline, SoftOutline,
///<summary> text with a glow effect.</summary> ///<summary> text with a glow effect.</summary>
Glow, Glow,
///<summary> text with both outline and shadow effects.</summary> ///<summary> text with both outline and shadow effects.</summary>
OutlineShadow, OutlineShadow,
///<summary> text with (far) shadow underneath.</summary> ///<summary> text with (far) shadow underneath.</summary>
FarShadow, FarShadow,
///<summary> text with outline and soft shadow effects combined.</summary> ///<summary> text with outline and soft shadow effects combined.</summary>
OutlineSoftShadow, OutlineSoftShadow,
///<summary> text with (soft) shadow underneath.</summary> ///<summary> text with (soft) shadow underneath.</summary>
SoftShadow, SoftShadow,
///<summary> text with (far soft) shadow underneath.</summary> ///<summary> text with (far soft) shadow underneath.</summary>
FarSoftShadow, FarSoftShadow,
// Shadow direction modifiers // Shadow direction modifiers
///<summary> shadow growing to bottom right.</summary> ///<summary> shadow growing to bottom right.</summary>
ShadowDirectionBottomRight = 0 /* 0 >> 4 */, ShadowDirectionBottomRight = 0 /* 0 >> 4 */,
///<summary> shadow growing to the bottom.</summary> ///<summary> shadow growing to the bottom.</summary>
ShadowDirectionBottom= 16 /* 1 >> 4 */, ShadowDirectionBottom = 16 /* 1 >> 4 */,
///<summary> shadow growing to bottom left.</summary> ///<summary> shadow growing to bottom left.</summary>
ShadowDirectionBottomLeft = 32 /* 2 >> 4 */, ShadowDirectionBottomLeft = 32 /* 2 >> 4 */,
///<summary> shadow growing to the left.</summary> ///<summary> shadow growing to the left.</summary>
ShadowDirectionLeft = 48 /* 3 >> 4 */, ShadowDirectionLeft = 48 /* 3 >> 4 */,
///<summary> shadow growing to top left.</summary> ///<summary> shadow growing to top left.</summary>
ShadowDirectionTopLeft = 64 /* 4 >> 4 */, ShadowDirectionTopLeft = 64 /* 4 >> 4 */,
///<summary> shadow growing to the top.</summary> ///<summary> shadow growing to the top.</summary>
ShadowDirectionTop = 80 /* 5 >> 4 */, ShadowDirectionTop = 80 /* 5 >> 4 */,
///<summary> shadow growing to top right.</summary> ///<summary> shadow growing to top right.</summary>
ShadowDirectionTopRight = 96 /* 6 >> 4 */, ShadowDirectionTopRight = 96 /* 6 >> 4 */,
///<summary> shadow growing to the right.</summary> ///<summary> shadow growing to the right.</summary>
ShadowDirectionRight = 112 /* 7 >> 4 */ ShadowDirectionRight = 112 /* 7 >> 4 */
}; };
} // namespace Evas } // namespace Evas
@ -201,8 +226,8 @@ public enum TextStyleType
public delegate int Eina_Compare_Cb(IntPtr a, IntPtr b); public delegate int Eina_Compare_Cb(IntPtr a, IntPtr b);
public delegate void ElmInterfaceScrollableCb(IntPtr obj, IntPtr data); public delegate void ElmInterfaceScrollableCb(IntPtr obj, IntPtr data);
public delegate void ElmInterfaceScrollableMinLimitCb(IntPtr obj, public delegate void ElmInterfaceScrollableMinLimitCb(IntPtr obj,
[MarshalAsAttribute(UnmanagedType.U1)]bool w, [MarshalAsAttribute(UnmanagedType.U1)]bool w,
[MarshalAsAttribute(UnmanagedType.U1)]bool h); [MarshalAsAttribute(UnmanagedType.U1)]bool h);
public delegate void ElmInterfaceScrollableResizeCb(IntPtr obj, Evas.Coord w, Evas.Coord h); public delegate void ElmInterfaceScrollableResizeCb(IntPtr obj, Evas.Coord w, Evas.Coord h);
[return: MarshalAsAttribute(UnmanagedType.U1)] [return: MarshalAsAttribute(UnmanagedType.U1)]
public delegate bool ElmMultibuttonentryItemFilterCb(IntPtr obj, IntPtr item_label, IntPtr item_data, IntPtr data); public delegate bool ElmMultibuttonentryItemFilterCb(IntPtr obj, IntPtr item_label, IntPtr item_data, IntPtr data);

View File

@ -94,7 +94,8 @@ blacklisted_files = [
efl_mono_lib = library('eflcustomexportsmono', efl_mono_lib = library('eflcustomexportsmono',
join_paths('..', '..', 'lib', 'efl_mono', 'efl_custom_exports_mono.c'), join_paths('..', '..', 'lib', 'efl_mono', 'efl_custom_exports_mono.c'),
install : true, install : true,
dependencies : [eo, eina] install_dir : join_paths(dir_lib, 'efl-mono-'+version_major),
dependencies : [eo, eina, ecore]
) )
beta_option = [] beta_option = []

View File

@ -68,8 +68,6 @@ collections {
} }
program { program {
name: "animation,state1"; name: "animation,state1";
signal: "animation,start";
source: "";
in: 1.0 0.0; in: 1.0 0.0;
action: STATE_SET "invert" 1.0; action: STATE_SET "invert" 1.0;
target: "part_one"; target: "part_one";
@ -80,8 +78,6 @@ collections {
} }
program { program {
name: "animation,state2"; name: "animation,state2";
signal: "animation,start";
source: "";
in: 1.0 0.0; in: 1.0 0.0;
action: STATE_SET "default" 0.0; action: STATE_SET "default" 0.0;
target: "part_one"; target: "part_one";

View File

@ -72,7 +72,7 @@ foreach edc_file : edc_files
'-md', meson.current_source_dir(), '-md', meson.current_source_dir(),
'-td', meson.current_source_dir(), '-td', meson.current_source_dir(),
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, ) depends : edje_depends, )
endforeach endforeach
codegen = custom_target('edje_cc_codegen_edc', codegen = custom_target('edje_cc_codegen_edc',
@ -87,7 +87,7 @@ codegen = custom_target('edje_cc_codegen_edc',
'-md', meson.current_source_dir(), '-md', meson.current_source_dir(),
'-td', meson.current_source_dir(), '-td', meson.current_source_dir(),
'@INPUT@', '@OUTPUT@'], '@INPUT@', '@OUTPUT@'],
depends : edje_cc, ) depends : edje_depends, )
themes += custom_target('edje_codegen_codegen.edj', themes += custom_target('edje_codegen_codegen.edj',
input : codegen, input : codegen,

View File

@ -131,7 +131,7 @@ themes = []
foreach edc_file : edc_files foreach edc_file : edc_files
themes += custom_target('edje_cc_' + edc_file, themes += custom_target('edje_cc_' + edc_file,
depends : edje_cc, depends : edje_depends,
input : edc_file, input : edc_file,
output : '@BASENAME@.edj', output : '@BASENAME@.edj',
command : edje_cc_exe + ['-beta', command : edje_cc_exe + ['-beta',

View File

@ -12,7 +12,7 @@ themes = []
foreach edc_file : edc_files foreach edc_file : edc_files
themes += custom_target('edje_cc_' + edc_file, themes += custom_target('edje_cc_' + edc_file,
depends : edje_cc, depends : edje_depends,
input : edc_file, input : edc_file,
output : '@BASENAME@.edj', output : '@BASENAME@.edj',
command : edje_cc_exe + ['-beta', command : edje_cc_exe + ['-beta',

View File

@ -10,7 +10,7 @@ themes = []
foreach edc_file : edc_files foreach edc_file : edc_files
themes += custom_target('edje_cc_' + edc_file, themes += custom_target('edje_cc_' + edc_file,
depends : edje_cc, depends : edje_depends,
input : edc_file, input : edc_file,
output : '@BASENAME@.edj', output : '@BASENAME@.edj',
command : edje_cc_exe + ['-beta', command : edje_cc_exe + ['-beta',

View File

@ -67,7 +67,7 @@ EAPI int ecore_shutdown(void);
* should call ecore_init() first, then register your callback on * should call ecore_init() first, then register your callback on
* @c EFL_LOOP_EVENT_ARGUMENTS and finally call ecore_init_ex(). * @c EFL_LOOP_EVENT_ARGUMENTS and finally call ecore_init_ex().
* *
* Once you are shuting down your program, you should symetrically * Once you are shuting down your program, you should symmetrically
* call ecore_shutdown_ex(). * call ecore_shutdown_ex().
*/ */
EAPI unsigned int ecore_init_ex(int argc, char **argv); EAPI unsigned int ecore_init_ex(int argc, char **argv);

View File

@ -571,10 +571,13 @@ ecore_fork_reset(void)
EINA_LIST_FOREACH_SAFE(_thread_cb, l, ln, call) EINA_LIST_FOREACH_SAFE(_thread_cb, l, ln, call)
{ {
if (call->suspend || call->sync) continue; //if something is supsend, then the mainloop will be blocked until until thread is calling ecore_thread_main_loop_end()
if (call->cb.async != (Ecore_Cb)&_ecore_thread_join) continue; //if something tries to join a thread as callback, ensure that we remove this
_thread_cb = eina_list_remove_list(_thread_cb, l); if (call->suspend || (call->cb.async == (Ecore_Cb)&_ecore_thread_join))
free(call); {
_thread_cb = eina_list_remove_list(_thread_cb, l);
free(call);
}
} }
if (_thread_cb) ecore_pipe_write(_thread_call, &wakeup, sizeof (int)); if (_thread_cb) ecore_pipe_write(_thread_call, &wakeup, sizeof (int));
} }
@ -686,7 +689,7 @@ ecore_thread_main_loop_begin(void)
return ++_thread_loop; return ++_thread_loop;
} }
order = malloc(sizeof (Ecore_Safe_Call)); order = calloc(1, sizeof (Ecore_Safe_Call));
if (!order) return -1; if (!order) return -1;
eina_lock_take(&_thread_id_lock); eina_lock_take(&_thread_id_lock);

View File

@ -44,7 +44,7 @@ class @beta Efl.Exe extends Efl.Task implements Efl.Io.Reader, Efl.Io.Writer, Ef
} }
@property env { @property env {
[[ If $env is $null then the process created by this object is [[ If $env is $null then the process created by this object is
going to inherit the enviroment of this process. going to inherit the environment of this process.
In case $env is not $null then the environment variables declared In case $env is not $null then the environment variables declared
in this object will represent the environment passed to the new process. in this object will represent the environment passed to the new process.

View File

@ -47,7 +47,7 @@ typedef struct _Ecore_Cocoa_Screen Ecore_Cocoa_Screen;
/** /**
* @typedef Ecore_Cocoa_Object * @typedef Ecore_Cocoa_Object
* Opaque handler to refer to an objective-c object (aka id) * Opaque handler to refer to an objective-c object (a.k.a. id)
* @since 1.18 * @since 1.18
*/ */
typedef void Ecore_Cocoa_Object; typedef void Ecore_Cocoa_Object;

View File

@ -38,11 +38,8 @@
# include <systemd/sd-daemon.h> # include <systemd/sd-daemon.h>
#endif #endif
#ifdef HAVE_WS2TCPIP_H
# include <ws2tcpip.h>
#endif
#ifdef _WIN32 #ifdef _WIN32
# include <ws2tcpip.h>
# include <Evil.h> # include <Evil.h>
#endif #endif

View File

@ -17,7 +17,7 @@
# include <systemd/sd-daemon.h> # include <systemd/sd-daemon.h>
#endif #endif
#ifdef HAVE_WS2TCPIP_H #ifdef _WIN32
# include <ws2tcpip.h> # include <ws2tcpip.h>
#endif #endif

View File

@ -34,11 +34,8 @@
# include <net/if.h> # include <net/if.h>
#endif #endif
#ifdef HAVE_WS2TCPIP_H
# include <ws2tcpip.h>
#endif
#ifdef _WIN32 #ifdef _WIN32
# include <ws2tcpip.h>
# include <Evil.h> # include <Evil.h>
#endif #endif

View File

@ -8,7 +8,7 @@
#include <sys/types.h> #include <sys/types.h>
#include <unistd.h> #include <unistd.h>
#ifdef HAVE_WS2TCPIP_H #ifdef _WIN32
# include <ws2tcpip.h> # include <ws2tcpip.h>
#endif #endif

View File

@ -72,7 +72,7 @@ class @beta Efl.Net.Dialer_Http extends Efl.Loop_Consumer implements Efl.Net.Dia
- If @Efl.Net.Dialer_Http_Primary_Mode.auto, then - If @Efl.Net.Dialer_Http_Primary_Mode.auto, then
@Efl.Net.Dialer_Http_Primary_Mode.download or @Efl.Net.Dialer_Http_Primary_Mode.download or
@Efl.Net.Dialer_Http_Primary_Mode.upload will be @Efl.Net.Dialer_Http_Primary_Mode.upload will be
choosen based on the @.method: if "PUT", then it's chosen based on the @.method: if "PUT", then it's
upload, otherwise it's download. upload, otherwise it's download.
- If @Efl.Net.Dialer_Http_Primary_Mode.upload, applying - If @Efl.Net.Dialer_Http_Primary_Mode.upload, applying

View File

@ -2,10 +2,7 @@ ecore_con_deps = []
ecore_con_pub_deps = [eina, eo, efl, ecore] ecore_con_pub_deps = [eina, eo, efl, ecore]
if sys_windows == true if sys_windows == true
ipv6 = cc.compiles(''' ipv6 = true
#include <ws2tcpip.h>
struct ipv6_mreq tmp;
''')
else else
ipv6 = cc.compiles(''' ipv6 = cc.compiles('''
#include <netinet/in.h> #include <netinet/in.h>

View File

@ -510,6 +510,16 @@ _fb_flip(Ecore_Drm2_Output *output)
int ret = 0; int ret = 0;
fb = output->prep.fb; fb = output->prep.fb;
if (!fb)
{
fb = output->pending.fb;
ERR("Trying to flip NULL fb - fallback to pending fb");
}
if (!fb)
{
ERR("Pending fb is also NULL, give up flipping");
return ret;
}
if ((!output->current.fb) || if ((!output->current.fb) ||
(output->current.fb->strides[0] != fb->strides[0])) (output->current.fb->strides[0] != fb->strides[0]))

View File

@ -33,7 +33,7 @@ void
ecore_imf_module_init(void) ecore_imf_module_init(void)
{ {
const char *built_modules[] = { const char *built_modules[] = {
#ifdef ENABLE_XIM #ifdef BUILD_ECORE_IMF_XIM
"xim", "xim",
#endif #endif
#ifdef BUILD_ECORE_IMF_IBUS #ifdef BUILD_ECORE_IMF_IBUS

View File

@ -1482,7 +1482,7 @@ EAPI Ecore_Wl2_Offer* ecore_wl2_dnd_selection_get(Ecore_Wl2_Input *input);
* *
* @param types a null-terminated array of mimetypes supported by the client * @param types a null-terminated array of mimetypes supported by the client
* *
* @return serial of request on sucess, 0 on failure * @return serial of request on success, 0 on failure
* *
* @ingroup Ecore_Wl2_Dnd_Group * @ingroup Ecore_Wl2_Dnd_Group
* @since 1.17 * @since 1.17
@ -1494,7 +1494,7 @@ EAPI uint32_t ecore_wl2_dnd_selection_set(Ecore_Wl2_Input *input, const char **t
* *
* @param input the input to clear * @param input the input to clear
* *
* @return serial of request on sucess, 0 on failure * @return serial of request on success, 0 on failure
* *
* @ingroup Ecore_Wl2_Dnd_Group * @ingroup Ecore_Wl2_Dnd_Group
* @since 1.17 * @since 1.17

View File

@ -2763,7 +2763,7 @@ EAPI Eina_Bool ecore_x_window_keygrab_unset(Ecore_X_
//this API for keyrouter protocol //this API for keyrouter protocol
EAPI void ecore_x_e_keyrouter_set(Ecore_X_Window root, Eina_Bool on); /**< @since 1.15 */ //Key router set keyrouter flag using this EAPI void ecore_x_e_keyrouter_set(Ecore_X_Window root, Eina_Bool on); /**< @since 1.15 */ //Key router set keyrouter flag using this
EAPI Eina_Bool ecore_x_e_keyrouter_get(Ecore_X_Window root); /**< @since 1.15 */ //Client check the existance of keyrouter using this EAPI Eina_Bool ecore_x_e_keyrouter_get(Ecore_X_Window root); /**< @since 1.15 */ //Client check the existence of keyrouter using this
#ifdef EFL_BETA_API_SUPPORT #ifdef EFL_BETA_API_SUPPORT
// XXX: FIXME: re-evaluate this after looking at xdg foreign in wayland // XXX: FIXME: re-evaluate this after looking at xdg foreign in wayland

View File

@ -100,7 +100,7 @@ typedef Eo Ector_Renderer;
/** /**
* @typedef Ector_Colorspace * @typedef Ector_Colorspace
* The definiton of colorspace. * The definition of colorspace.
*/ */
// FIXME: Enable this when we have merged Emile // FIXME: Enable this when we have merged Emile
/* typedef Evas_Colorspace Ector_Colorspace; */ /* typedef Evas_Colorspace Ector_Colorspace; */

View File

@ -426,7 +426,7 @@ EAPI int edje_object_freeze(Evas_Object *obj);
* *
* This function thaws the given Edje object. * This function thaws the given Edje object.
* *
* @note If sucessive freezes were done, an equal number of thaws will be * @note If successive freezes were done, an equal number of thaws will be
* required. * required.
* *
* See also @ref edje_object_freeze() * See also @ref edje_object_freeze()

View File

@ -193,13 +193,13 @@ Edje_Part_Collection *_edje_collection_convert(Edje_File *file,
Old_Edje_Part_Collection *oedc); Old_Edje_Part_Collection *oedc);
/** /**
* Convert old Edje part descripton into new format. * Convert old Edje part description into new format.
* *
* @param type The edje par description common type * @param type The edje par description common type
* @param ce an edje collection directory entry * @param ce an edje collection directory entry
* @param the old edje part descripton * @param the old edje part description
* *
* @return a new edje part descripton common * @return a new edje part description common
*/ */
Edje_Part_Description_Common *_edje_description_convert(int type, Edje_Part_Description_Common *_edje_description_convert(int type,
Edje_Part_Collection_Directory_Entry *ce, Edje_Part_Collection_Directory_Entry *ce,

View File

@ -90,7 +90,7 @@ interface Efl.Layout.Calc
This function thaws (in other words "unfreezes") the given layout This function thaws (in other words "unfreezes") the given layout
object. object.
Note: If sucessive freezes were done, an equal number of thaws will Note: If successive freezes were done, an equal number of thaws will
be required. be required.
See also @.calc_freeze. See also @.calc_freeze.

View File

@ -9,7 +9,7 @@
*/ */
function EflLayoutSignalCb { function EflLayoutSignalCb {
[[EflLayoutSignalCb function that is called when a specifc pair of signal/emision is triggered [[EflLayoutSignalCb function that is called when a specifc pair of signal/emission is triggered
@since 1.22 @since 1.22
]] ]]

View File

@ -1467,7 +1467,7 @@ eet_data_image_header_read_cipher(Eet_File *ef,
/** /**
* @ingroup Eet_File_Image_Group * @ingroup Eet_File_Image_Group
* @brief Gets the colorspace Eet can decode into of a given eet image ressource. * @brief Gets the colorspace Eet can decode into of a given eet image resource.
* *
* @param ef A valid eet file handle opened for reading. * @param ef A valid eet file handle opened for reading.
* @param name Name of the entry. eg: "/base/file_i_want". * @param name Name of the entry. eg: "/base/file_i_want".

View File

@ -50,6 +50,8 @@ extern "C" {
#define EFL_VERSION_1_19 1 #define EFL_VERSION_1_19 1
#define EFL_VERSION_1_20 1 #define EFL_VERSION_1_20 1
#define EFL_VERSION_1_21 1 #define EFL_VERSION_1_21 1
#define EFL_VERSION_1_22 1
#define EFL_VERSION_1_23 1
/* Add here all the required ifdef for any @protected method */ /* Add here all the required ifdef for any @protected method */
#ifdef EFL_BUILD #ifdef EFL_BUILD

View File

@ -1,5 +1,4 @@
import eina_types; import eina_types;
import efl_gfx_types;
mixin Efl.File requires Efl.Object { mixin Efl.File requires Efl.Object {
[[Efl file interface [[Efl file interface
@ -10,23 +9,21 @@ mixin Efl.File requires Efl.Object {
@property mmap { @property mmap {
set { set {
[[Set the mmaped file from where an object will fetch the real [[Set the mmaped file from where an object will fetch the real
data (it must be an Eina_File). data (it must be an @Eina.File).
If mmap is set during object construction, the object will automatically If mmap is set during object construction, the object will automatically
call @.load during the finalize phase of construction. call @.load during the finalize phase of construction.
]]
]]
return: Eina.Error; [[0 on success, error code otherwise]] return: Eina.Error; [[0 on success, error code otherwise]]
} }
get { get {
[[Get the mmaped file from where an object will fetch the real [[Get the mmaped file from where an object will fetch the real
data (it must be an Eina_File). data (it must be an @Eina.File).
]]
]]
} }
values { values {
f: ptr(const(Eina.File)); [[The handle to an Eina_File that will be used]] f: ptr(const(Eina.File)); [[The handle to the @Eina.File that will be used]]
} }
} }
@property file { @property file {
@ -42,7 +39,8 @@ mixin Efl.File requires Efl.Object {
get { get {
[[Retrieve the file path from where an object is to fetch the data. [[Retrieve the file path from where an object is to fetch the data.
You must not modify the strings on the returned pointers.]] You must not modify the strings on the returned pointers.
]]
} }
values { values {
file: string; [[The file path.]] file: string; [[The file path.]]
@ -60,15 +58,16 @@ mixin Efl.File requires Efl.Object {
[[Get the previously-set key which corresponds to the target data within a file. [[Get the previously-set key which corresponds to the target data within a file.
Some filetypes can contain multiple data streams which are indexed by Some filetypes can contain multiple data streams which are indexed by
a key. Use this property for such cases. a key. Use this property for such cases (See for example @Efl.Ui.Image or
@Efl.Ui.Layout).
You must not modify the strings on the returned pointers.]] You must not modify the strings on the returned pointers.
]]
} }
values { values {
key: string; [[The group that the image belongs to, in case key: string; [[The group that the data belongs to. See the class documentation
it's an EET(including Edje case) file. This can be used for particular implementations of this interface to see how this
as a key inside evas image cache if this is a normal image property is used.]]
file not eet file.]]
} }
} }
@property loaded { @property loaded {
@ -77,7 +76,7 @@ mixin Efl.File requires Efl.Object {
]] ]]
} }
values { values {
loaded: bool; [[True if the object is loaded, otherwise false.]] loaded: bool; [[$true if the object is loaded, $false otherwise.]]
} }
} }
@ -89,9 +88,10 @@ mixin Efl.File requires Efl.Object {
open the file and call @.mmap.set on the object using the opened file handle. open the file and call @.mmap.set on the object using the opened file handle.
Calling @.load on an object which has already performed file operations based on Calling @.load on an object which has already performed file operations based on
the currently set properties will have no effect.]] the currently set properties will have no effect.
]]
return: Eina.Error; [[0 on success, error code otherwise]] return: Eina.Error; [[0 on success, error code otherwise]]
} }
unload { unload {

View File

@ -17,9 +17,9 @@ interface @beta Efl.Pack_Layout
[[Implementation of this container's layout algorithm. [[Implementation of this container's layout algorithm.
EFL will call this function whenever the contents of this EFL will call this function whenever the contents of this
container need to be re-layed out on the canvas. container need to be re-laid out on the canvas.
This can be overriden to implement custom layout behaviours. This can be overriden to implement custom layout behaviors.
]] ]]
} }
} }

View File

@ -1,5 +1,6 @@
#include "Eo.h" #include "Eo.h"
#include "Eina.h" #include "Eina.h"
#include "Ecore.h"
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
@ -22,6 +23,92 @@
# endif # endif
#endif /* ! _WIN32 */ #endif /* ! _WIN32 */
typedef void (*Efl_Mono_Free_GCHandle_Cb)(void *gchandle);
typedef void (*Efl_Mono_Remove_Events_Cb)(Eo *obj, void *gchandle);
static Efl_Mono_Free_GCHandle_Cb _efl_mono_free_gchandle_call = NULL;
static Efl_Mono_Remove_Events_Cb _efl_mono_remove_events_call = NULL;
EAPI void efl_mono_gchandle_callbacks_set(Efl_Mono_Free_GCHandle_Cb free_gchandle_cb, Efl_Mono_Remove_Events_Cb remove_events_cb)
{
_efl_mono_free_gchandle_call = free_gchandle_cb;
_efl_mono_remove_events_call = remove_events_cb;
}
EAPI void efl_mono_native_dispose(Eo *obj, void* gchandle)
{
if (gchandle) _efl_mono_remove_events_call(obj, gchandle);
efl_unref(obj);
if (gchandle) _efl_mono_free_gchandle_call(gchandle);
}
typedef struct _Efl_Mono_Native_Dispose_Data
{
Eo *obj;
void *gchandle;
} Efl_Mono_Native_Dispose_Data;
static void _efl_mono_native_dispose_cb(void *data)
{
Efl_Mono_Native_Dispose_Data *dd = data;
efl_mono_native_dispose(dd->obj, dd->gchandle);
free(dd);
}
EAPI void efl_mono_thread_safe_native_dispose(Eo *obj, void* gchandle)
{
Efl_Mono_Native_Dispose_Data *dd = malloc(sizeof(Efl_Mono_Native_Dispose_Data));
dd->obj = obj;
dd->gchandle = gchandle;
ecore_main_loop_thread_safe_call_async(_efl_mono_native_dispose_cb, dd);
}
static void _efl_mono_unref_cb(void *obj)
{
efl_unref(obj);
}
EAPI void efl_mono_thread_safe_efl_unref(Eo* obj)
{
ecore_main_loop_thread_safe_call_async(_efl_mono_unref_cb, obj);
}
EAPI void efl_mono_thread_safe_free_cb_exec(Eina_Free_Cb free_cb, void* cb_data)
{
ecore_main_loop_thread_safe_call_async(free_cb, cb_data);
}
static void _efl_mono_list_free_cb(void *l)
{
eina_list_free(l);
}
EAPI void efl_mono_thread_safe_eina_list_free(Eina_List* list)
{
ecore_main_loop_thread_safe_call_async(_efl_mono_list_free_cb, list);
}
typedef struct _Efl_Mono_Promise_Reject_Data
{
Eina_Promise *promise;
Eina_Error err;
} Efl_Mono_Promise_Reject_Data;
static void _efl_mono_promise_reject_cb(void *data)
{
Efl_Mono_Promise_Reject_Data *d = data;
eina_promise_reject(d->promise, d->err);
free(d);
}
EAPI void efl_mono_thread_safe_promise_reject(Eina_Promise *p, Eina_Error err)
{
Efl_Mono_Promise_Reject_Data *d = malloc(sizeof(Efl_Mono_Promise_Reject_Data));
d->promise = p;
d->err = err;
ecore_main_loop_thread_safe_call_async(_efl_mono_promise_reject_cb, d);
}
EAPI void *efl_mono_native_alloc(unsigned int size) EAPI void *efl_mono_native_alloc(unsigned int size)
{ {
return malloc(size); return malloc(size);
@ -81,7 +168,7 @@ EAPI Eina_Free_Cb efl_mono_native_free_addr_get()
EAPI Eina_Free_Cb efl_mono_native_efl_unref_addr_get() EAPI Eina_Free_Cb efl_mono_native_efl_unref_addr_get()
{ {
return (Eina_Free_Cb)efl_unref; return (Eina_Free_Cb)efl_mono_thread_safe_efl_unref;
} }
// Iterator Wrapper // // Iterator Wrapper //

View File

@ -52,7 +52,7 @@ typedef struct _Eina_Future_Cb_Log_Desc Eina_Future_Cb_Log_Desc;
* *
* @return An Eina_Value to pass to the next Eina_Future in the chain (if any). * @return An Eina_Value to pass to the next Eina_Future in the chain (if any).
* If there is no need to convert the received value, it's @b recommended * If there is no need to convert the received value, it's @b recommended
* to pass-thru @p value argument. If you need to convert to a different type * to passthrough @p value argument. If you need to convert to a different type
* or generate a new value, use @c eina_value_setup() on @b another Eina_Value * or generate a new value, use @c eina_value_setup() on @b another Eina_Value
* and return it. By returning a promise Eina_Value (eina_promise_as_value()) the * and return it. By returning a promise Eina_Value (eina_promise_as_value()) the
* whole chain will wait until the promise is resolved in * whole chain will wait until the promise is resolved in
@ -205,7 +205,7 @@ typedef void (*Eina_Promise_Cancel_Cb) (void *data, const Eina_Promise *dead_pro
* @param[in] value The operation result * @param[in] value The operation result
* @return An Eina_Value to pass to the next Eina_Future in the chain (if any). * @return An Eina_Value to pass to the next Eina_Future in the chain (if any).
* If there is no need to convert the received value, it's @b recommended * If there is no need to convert the received value, it's @b recommended
* to pass-thru @p value argument. If you need to convert to a different type * to passthrough @p value argument. If you need to convert to a different type
* or generate a new value, use @c eina_value_setup() on @b another Eina_Value * or generate a new value, use @c eina_value_setup() on @b another Eina_Value
* and return it. By returning a promise Eina_Value (eina_promise_as_value()) the * and return it. By returning a promise Eina_Value (eina_promise_as_value()) the
* whole chain will wait until the promise is resolved in * whole chain will wait until the promise is resolved in
@ -302,7 +302,7 @@ struct _Eina_Future_Cb_Easy_Desc {
* may also return a non-error, in this case the next future in chain will receive a regular * may also return a non-error, in this case the next future in chain will receive a regular
* value, which may call its @c success. * value, which may call its @c success.
* *
* If this function is not provided, then it will pass thru the error to the next error handler. * If this function is not provided, then it will passthrough the error to the next error handler.
* *
* It may be called with @c EINVAL if @c success_type is provided and doesn't * It may be called with @c EINVAL if @c success_type is provided and doesn't
* match the received type. * match the received type.

View File

@ -109,7 +109,7 @@ class @beta Efl.Io.Manager extends Efl.Loop_Consumer
[[Closes an open Eina.File.]] [[Closes an open Eina.File.]]
params { params {
@in file: ptr(Eina.File); [[Eina file handle]] @in file: ptr(Eina.File); [[Eina file handle]]
// Here we're just interested whether the promise was fullfilled or not. No value needed. // Here we're just interested whether the promise was fulfilled or not. No value needed.
} }
return: future<int> @owned; [[Close return code]] return: future<int> @owned; [[Close return code]]
} }

Some files were not shown because too many files have changed in this diff Show More