summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMun, Gwan-gyeong <kk.moon@samsung.com>2014-12-04 17:59:30 +0900
committerGwanglim Lee <gl77.lee@samsung.com>2014-12-04 17:59:30 +0900
commitd1b8d52e0edd5de0e0c152021affd2c3c43775d7 (patch)
tree9d82fc499fe1a3a7cce19b2302a3c97205d32e96
parent83512198b893845b25c4f5afd49dbea945809ead (diff)
evas/gl_drm: add native surface for wayland_egl_client.
Reviewers: zmike, devilhorns, cedric, gwanglim Reviewed By: cedric, gwanglim Subscribers: jpeg, torori, cedric Differential Revision: https://phab.enlightenment.org/D1507
-rw-r--r--m4/evas_check_engine.m44
-rw-r--r--src/lib/evas/Evas_Common.h13
-rw-r--r--src/modules/ecore_evas/engines/drm/ecore_evas_drm.c4
-rw-r--r--src/modules/evas/engines/gl_common/evas_gl_common.h1
-rw-r--r--src/modules/evas/engines/gl_common/evas_gl_context.c2
-rw-r--r--src/modules/evas/engines/gl_drm/evas_engine.c326
6 files changed, 340 insertions, 10 deletions
diff --git a/m4/evas_check_engine.m4 b/m4/evas_check_engine.m4
index 6b2ca60..5dc333f 100644
--- a/m4/evas_check_engine.m4
+++ b/m4/evas_check_engine.m4
@@ -654,10 +654,10 @@ evas_engine_[]$1[]_libs=""
654 654
655gl_library="glesv2" 655gl_library="glesv2"
656 656
657PKG_CHECK_EXISTS([egl >= 7.10 ${gl_library} gbm], 657PKG_CHECK_EXISTS([egl >= 7.10 ${gl_library} gbm wayland-client >= 1.3.0],
658 [ 658 [
659 have_dep="yes" 659 have_dep="yes"
660 requirement="egl >= 7.10 ${gl_library} gbm" 660 requirement="egl >= 7.10 ${gl_library} gbm wayland-client >= 1.3.0"
661 ], 661 ],
662 [have_dep="no"]) 662 [have_dep="no"])
663 663
diff --git a/src/lib/evas/Evas_Common.h b/src/lib/evas/Evas_Common.h
index dfffa14..722bb0c 100644
--- a/src/lib/evas/Evas_Common.h
+++ b/src/lib/evas/Evas_Common.h
@@ -461,7 +461,7 @@ struct _Evas_Pixel_Import_Source
461 * Magic version number to know what the native surface struct looks like 461 * Magic version number to know what the native surface struct looks like
462 */ 462 */
463 463
464#define EVAS_NATIVE_SURFACE_VERSION 2 464#define EVAS_NATIVE_SURFACE_VERSION 3
465 465
466/** 466/**
467 * Native surface types that image object supports 467 * Native surface types that image object supports
@@ -473,7 +473,8 @@ typedef enum _Evas_Native_Surface_Type
473{ 473{
474 EVAS_NATIVE_SURFACE_NONE, /**< No surface type */ 474 EVAS_NATIVE_SURFACE_NONE, /**< No surface type */
475 EVAS_NATIVE_SURFACE_X11, /**< X Window system based type. pixmap id or visual of the pixmap */ 475 EVAS_NATIVE_SURFACE_X11, /**< X Window system based type. pixmap id or visual of the pixmap */
476 EVAS_NATIVE_SURFACE_OPENGL /**< OpenGL system based type. texture or framebuffer id*/ 476 EVAS_NATIVE_SURFACE_OPENGL, /**< OpenGL system based type. texture or framebuffer id*/
477 EVAS_NATIVE_SURFACE_WL /**< Wayland system based type. buffer of surface */
477} Evas_Native_Surface_Type; 478} Evas_Native_Surface_Type;
478 479
479/** 480/**
@@ -484,7 +485,9 @@ typedef enum _Evas_Native_Surface_Type
484 * EVAS_NATIVE_SURFACE_X11, you need to set union data with x11.visual or 485 * EVAS_NATIVE_SURFACE_X11, you need to set union data with x11.visual or
485 * x11.pixmap. If you need to set the native surface as 486 * x11.pixmap. If you need to set the native surface as
486 * EVAS_NATIVE_SURFACE_OPENGL, on the other hand, you need to set union data 487 * EVAS_NATIVE_SURFACE_OPENGL, on the other hand, you need to set union data
487 * with opengl.texture_id or opengl.framebuffer_id and so on. The version field 488 * with opengl.texture_id or opengl.framebuffer_id and so on.
489 * If you need to set the native surface as EVAS_NATIVE_SURFACE_WL,
490 * you need to set union data with wl.legacy_buffer. The version field
488 * should be set with EVAS_NATIVE_SURFACE_VERSION in order to check abi 491 * should be set with EVAS_NATIVE_SURFACE_VERSION in order to check abi
489 * break in your application on the different efl library versions. 492 * break in your application on the different efl library versions.
490 * 493 *
@@ -518,6 +521,10 @@ struct _Evas_Native_Surface
518 unsigned int format; /**< same as 'format' for glTexImage2D() */ 521 unsigned int format; /**< same as 'format' for glTexImage2D() */
519 unsigned int x, y, w, h; /**< region inside the texture to use (image size is assumed as texture size, with 0, 0 being the top-left and co-ordinates working down to the right and bottom being positive) */ 522 unsigned int x, y, w, h; /**< region inside the texture to use (image size is assumed as texture size, with 0, 0 being the top-left and co-ordinates working down to the right and bottom being positive) */
520 } opengl; /**< Set this struct fields if surface data is OpenGL based. */ 523 } opengl; /**< Set this struct fields if surface data is OpenGL based. */
524 struct
525 {
526 void *legacy_buffer; /**< wayland client buffer to use */
527 } wl; /**< Set this struct fields if surface data is Wayland based. */
521 } data; /**< Choose one union data according to your surface. */ 528 } data; /**< Choose one union data according to your surface. */
522}; 529};
523 530
diff --git a/src/modules/ecore_evas/engines/drm/ecore_evas_drm.c b/src/modules/ecore_evas/engines/drm/ecore_evas_drm.c
index e47283e..ce6ce84 100644
--- a/src/modules/ecore_evas/engines/drm/ecore_evas_drm.c
+++ b/src/modules/ecore_evas/engines/drm/ecore_evas_drm.c
@@ -555,10 +555,6 @@ _ecore_evas_drm_interface_new(void)
555 iface->base.name = "drm"; 555 iface->base.name = "drm";
556 iface->base.version = 1; 556 iface->base.version = 1;
557 557
558 /* iface->pixmap_visual_get; */
559 /* iface->pixmap_colormap_get; */
560 /* iface->pixmap_depth_get; */
561
562 return iface; 558 return iface;
563} 559}
564 560
diff --git a/src/modules/evas/engines/gl_common/evas_gl_common.h b/src/modules/evas/engines/gl_common/evas_gl_common.h
index 6d82623..87ea366 100644
--- a/src/modules/evas/engines/gl_common/evas_gl_common.h
+++ b/src/modules/evas/engines/gl_common/evas_gl_common.h
@@ -376,6 +376,7 @@ struct _Evas_GL_Shared
376 376
377 Eina_Hash *native_pm_hash; 377 Eina_Hash *native_pm_hash;
378 Eina_Hash *native_tex_hash; 378 Eina_Hash *native_tex_hash;
379 Eina_Hash *native_wl_hash;
379 380
380#ifdef GL_GLES 381#ifdef GL_GLES
381 // FIXME: hack. 382 // FIXME: hack.
diff --git a/src/modules/evas/engines/gl_common/evas_gl_context.c b/src/modules/evas/engines/gl_common/evas_gl_context.c
index 19c1a2e..32f10b8 100644
--- a/src/modules/evas/engines/gl_common/evas_gl_context.c
+++ b/src/modules/evas/engines/gl_common/evas_gl_context.c
@@ -867,6 +867,7 @@ evas_gl_common_context_new(void)
867 867
868 shared->native_pm_hash = eina_hash_int32_new(NULL); 868 shared->native_pm_hash = eina_hash_int32_new(NULL);
869 shared->native_tex_hash = eina_hash_int32_new(NULL); 869 shared->native_tex_hash = eina_hash_int32_new(NULL);
870 shared->native_wl_hash = eina_hash_pointer_new(NULL);
870 } 871 }
871 gc->shared = shared; 872 gc->shared = shared;
872 gc->shared->references++; 873 gc->shared->references++;
@@ -939,6 +940,7 @@ evas_gl_common_context_free(Evas_Engine_GL_Context *gc)
939 eina_list_free(gc->shared->tex.whole); 940 eina_list_free(gc->shared->tex.whole);
940 eina_hash_free(gc->shared->native_pm_hash); 941 eina_hash_free(gc->shared->native_pm_hash);
941 eina_hash_free(gc->shared->native_tex_hash); 942 eina_hash_free(gc->shared->native_tex_hash);
943 eina_hash_free(gc->shared->native_wl_hash);
942 free(gc->shared); 944 free(gc->shared);
943 shared = NULL; 945 shared = NULL;
944 } 946 }
diff --git a/src/modules/evas/engines/gl_drm/evas_engine.c b/src/modules/evas/engines/gl_drm/evas_engine.c
index 87f98bb..5155c4b 100644
--- a/src/modules/evas/engines/gl_drm/evas_engine.c
+++ b/src/modules/evas/engines/gl_drm/evas_engine.c
@@ -20,6 +20,7 @@
20# define EGL_NATIVE_PIXMAP_KHR 0x30b0 20# define EGL_NATIVE_PIXMAP_KHR 0x30b0
21#endif 21#endif
22 22
23#include <wayland-client.h>
23/* external variables */ 24/* external variables */
24int _evas_engine_gl_drm_log_dom = -1; 25int _evas_engine_gl_drm_log_dom = -1;
25int extn_have_buffer_age = 1; 26int extn_have_buffer_age = 1;
@@ -51,12 +52,19 @@ Evas_GL_Preload_Render_Call glsym_evas_gl_preload_render_relax = NULL;
51 52
52/* local structures */ 53/* local structures */
53typedef struct _Render_Engine Render_Engine; 54typedef struct _Render_Engine Render_Engine;
54
55struct _Render_Engine 55struct _Render_Engine
56{ 56{
57 Render_Engine_GL_Generic generic; 57 Render_Engine_GL_Generic generic;
58}; 58};
59 59
60typedef struct _Native Native;
61struct _Native
62{
63 Evas_Native_Surface ns;
64 struct wl_buffer *wl_buf;
65 void *egl_surface;
66};
67
60/* local function prototype types */ 68/* local function prototype types */
61typedef void (*_eng_fn) (void); 69typedef void (*_eng_fn) (void);
62typedef _eng_fn (*glsym_func_eng_fn) (); 70typedef _eng_fn (*glsym_func_eng_fn) ();
@@ -72,6 +80,7 @@ void *(*glsym_eglCreateImage)(EGLDisplay a, EGLContext b, EGLenum c, EGLClientBu
72void (*glsym_eglDestroyImage)(EGLDisplay a, void *b) = NULL; 80void (*glsym_eglDestroyImage)(EGLDisplay a, void *b) = NULL;
73void (*glsym_glEGLImageTargetTexture2DOES)(int a, void *b) = NULL; 81void (*glsym_glEGLImageTargetTexture2DOES)(int a, void *b) = NULL;
74unsigned int (*glsym_eglSwapBuffersWithDamage)(EGLDisplay a, void *b, const EGLint *d, EGLint c) = NULL; 82unsigned int (*glsym_eglSwapBuffersWithDamage)(EGLDisplay a, void *b, const EGLint *d, EGLint c) = NULL;
83unsigned int (*glsym_eglQueryWaylandBufferWL)(EGLDisplay a, struct wl_resource *b, EGLint c, EGLint *d) = NULL;
75 84
76/* local function prototypes */ 85/* local function prototypes */
77static void gl_symbols(void); 86static void gl_symbols(void);
@@ -194,6 +203,9 @@ gl_symbols(void)
194 FINDSYM(glsym_eglSwapBuffersWithDamage, "eglSwapBuffersWithDamage", 203 FINDSYM(glsym_eglSwapBuffersWithDamage, "eglSwapBuffersWithDamage",
195 glsym_func_uint); 204 glsym_func_uint);
196 205
206 FINDSYM(glsym_eglQueryWaylandBufferWL, "eglQueryWaylandBufferWL",
207 glsym_func_uint);
208
197 done = EINA_TRUE; 209 done = EINA_TRUE;
198} 210}
199 211
@@ -853,6 +865,317 @@ eng_output_dump(void *data)
853 _re_winfree(re); 865 _re_winfree(re);
854} 866}
855 867
868static void
869_native_cb_bind(void *data EINA_UNUSED, void *image)
870{
871 Evas_GL_Image *img;
872 Native *n;
873
874 if (!(img = image)) return;
875 if (!(n = img->native.data)) return;
876
877 if (n->ns.type == EVAS_NATIVE_SURFACE_WL)
878 {
879 if (n->egl_surface)
880 {
881 if (glsym_glEGLImageTargetTexture2DOES)
882 {
883 glsym_glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, n->egl_surface);
884 if (eglGetError() != EGL_SUCCESS)
885 ERR("glEGLImageTargetTexture2DOES() failed.");
886 }
887 else
888 ERR("Try glEGLImageTargetTexture2DOES on EGL with no support");
889 }
890 }
891 else if (n->ns.type == EVAS_NATIVE_SURFACE_OPENGL)
892 {
893 glBindTexture(GL_TEXTURE_2D, n->ns.data.opengl.texture_id);
894 GLERR(__FUNCTION__, __FILE__, __LINE__, "");
895 }
896}
897
898static void
899_native_cb_unbind(void *data EINA_UNUSED, void *image)
900{
901 Evas_GL_Image *img;
902 Native *n;
903
904 if (!(img = image)) return;
905 if (!(n = img->native.data)) return;
906
907 if (n->ns.type == EVAS_NATIVE_SURFACE_WL)
908 {
909 //glBindTexture(GL_TEXTURE_2D, 0); //really need?
910 GLERR(__FUNCTION__, __FILE__, __LINE__, "");
911 }
912 else if (n->ns.type == EVAS_NATIVE_SURFACE_OPENGL)
913 {
914 glBindTexture(GL_TEXTURE_2D, 0);
915 GLERR(__FUNCTION__, __FILE__, __LINE__, "");
916 }
917}
918
919static void
920_native_cb_free(void *data, void *image)
921{
922 Render_Engine *re;
923 Outbuf *ob;
924 Evas_GL_Image *img;
925 Native *n;
926 uint32_t texid;
927 void *wlid;
928
929 if (!(re = (Render_Engine *)data)) return;
930 if (!(img = image)) return;
931 if (!(n = img->native.data)) return;
932 if (!(ob = eng_get_ob(re))) return;
933
934 if (n->ns.type == EVAS_NATIVE_SURFACE_WL)
935 {
936 wlid = (void*)n->wl_buf;
937 eina_hash_del(ob->gl_context->shared->native_wl_hash, &wlid, img);
938 if (n->egl_surface)
939 {
940 if (glsym_eglDestroyImage)
941 {
942 glsym_eglDestroyImage(eng_get_ob(re)->egl_disp,
943 n->egl_surface);
944 if (eglGetError() != EGL_SUCCESS)
945 ERR("eglDestroyImage() failed.");
946 }
947 else
948 ERR("Try eglDestroyImage on EGL with no support");
949 }
950 }
951 else if (n->ns.type == EVAS_NATIVE_SURFACE_OPENGL)
952 {
953 texid = n->ns.data.opengl.texture_id;
954 eina_hash_del(ob->gl_context->shared->native_tex_hash, &texid, img);
955 }
956
957 img->native.data = NULL;
958 img->native.func.data = NULL;
959 img->native.func.bind = NULL;
960 img->native.func.unbind = NULL;
961 img->native.func.free = NULL;
962
963 free(n);
964}
965
966static void *
967eng_image_native_set(void *data, void *image, void *native)
968{
969 Render_Engine *re;
970 Outbuf *ob;
971 Native *n;
972 Evas_Native_Surface *ns;
973 Evas_GL_Image *img, *img2;
974 unsigned int tex = 0, fbo = 0;
975 uint32_t texid;
976 void *wlid;
977 void *wl_buf = NULL;
978
979 if (!(re = (Render_Engine *)data)) return NULL;
980 if (!(ob = eng_get_ob(re))) return NULL;
981
982 ns = native;
983
984 if (!(img = image))
985 {
986 if ((ns) && (ns->type == EVAS_NATIVE_SURFACE_OPENGL))
987 {
988 img =
989 glsym_evas_gl_common_image_new_from_data(ob->gl_context,
990 ns->data.opengl.w,
991 ns->data.opengl.h,
992 NULL, 1,
993 EVAS_COLORSPACE_ARGB8888);
994 }
995 else
996 return NULL;
997 }
998
999 if (ns)
1000 {
1001 if (ns->type == EVAS_NATIVE_SURFACE_WL)
1002 {
1003 wl_buf = ns->data.wl.legacy_buffer;
1004 if (img->native.data)
1005 {
1006 Evas_Native_Surface *ens;
1007
1008 ens = img->native.data;
1009 if (ens->data.wl.legacy_buffer == wl_buf)
1010 return img;
1011 }
1012 }
1013 else if (ns->type == EVAS_NATIVE_SURFACE_OPENGL)
1014 {
1015 tex = ns->data.opengl.texture_id;
1016 fbo = ns->data.opengl.framebuffer_id;
1017 if (img->native.data)
1018 {
1019 Evas_Native_Surface *ens;
1020
1021 ens = img->native.data;
1022 if ((ens->data.opengl.texture_id == tex) &&
1023 (ens->data.opengl.framebuffer_id == fbo))
1024 return img;
1025 }
1026 }
1027 }
1028
1029 if ((!ns) && (!img->native.data)) return img;
1030
1031 eng_window_use(ob);
1032
1033 if (img->native.data)
1034 {
1035 if (img->native.func.free)
1036 img->native.func.free(img->native.func.data, img);
1037 glsym_evas_gl_common_image_native_disable(img);
1038 }
1039
1040 if (!ns) return img;
1041
1042 if (ns->type == EVAS_NATIVE_SURFACE_WL)
1043 {
1044 wlid = wl_buf;
1045 img2 = eina_hash_find(ob->gl_context->shared->native_wl_hash, &wlid);
1046 if (img2 == img) return img;
1047 if (img2)
1048 {
1049 if((n = img2->native.data))
1050 {
1051 glsym_evas_gl_common_image_ref(img2);
1052 glsym_evas_gl_common_image_free(img);
1053 return img2;
1054 }
1055 }
1056 }
1057 else if (ns->type == EVAS_NATIVE_SURFACE_OPENGL)
1058 {
1059 texid = tex;
1060 img2 = eina_hash_find(ob->gl_context->shared->native_tex_hash, &texid);
1061 if (img2 == img) return img;
1062 if (img2)
1063 {
1064 if ((n = img2->native.data))
1065 {
1066 glsym_evas_gl_common_image_ref(img2);
1067 glsym_evas_gl_common_image_free(img);
1068 return img2;
1069 }
1070 }
1071 }
1072
1073 img2 = glsym_evas_gl_common_image_new_from_data(ob->gl_context, img->w,
1074 img->h, NULL, img->alpha,
1075 EVAS_COLORSPACE_ARGB8888);
1076 glsym_evas_gl_common_image_free(img);
1077
1078 if (!(img = img2)) return NULL;
1079
1080 if (ns->type == EVAS_NATIVE_SURFACE_WL)
1081 {
1082 if (native)
1083 {
1084 if ((n = calloc(1, sizeof(Native))))
1085 {
1086 EGLint attribs[3];
1087 int yinvert = 1;
1088 uint32_t format;
1089
1090 glsym_eglQueryWaylandBufferWL(ob->egl_disp, wl_buf, EGL_TEXTURE_FORMAT, &format);
1091 if ((format != EGL_TEXTURE_RGB) && (format != EGL_TEXTURE_RGBA))
1092 {
1093 ERR("eglQueryWaylandBufferWL() %d format is not supported ", format);
1094 glsym_evas_gl_common_image_free(img);
1095 free(n);
1096 return NULL;
1097 }
1098
1099 attribs[0] = EGL_WAYLAND_PLANE_WL;
1100 attribs[1] = 0; //if plane is 1 then 0, if plane is 2 then 1
1101 attribs[2] = EGL_NONE;
1102
1103 memcpy(&(n->ns), ns, sizeof(Evas_Native_Surface));
1104 glsym_eglQueryWaylandBufferWL(ob->egl_disp, wl_buf, EGL_WAYLAND_Y_INVERTED_WL, &yinvert);
1105 eina_hash_add(ob->gl_context->shared->native_wl_hash, &wlid, img);
1106
1107 n->wl_buf = wl_buf;
1108 if (glsym_eglCreateImage)
1109 n->egl_surface = glsym_eglCreateImage(ob->egl_disp,
1110 NULL,
1111 EGL_WAYLAND_BUFFER_WL,
1112 wl_buf,
1113 attribs);
1114 else
1115 {
1116 ERR("Try eglCreateImage on EGL with no support");
1117 eina_hash_del(ob->gl_context->shared->native_wl_hash, &wlid, img);
1118 glsym_evas_gl_common_image_free(img);
1119 free(n);
1120 return NULL;
1121 }
1122
1123 if (!n->egl_surface)
1124 {
1125 ERR("eglCreatePixmapSurface() for 0x%x failed", (unsigned int)wl_buf);
1126 eina_hash_del(ob->gl_context->shared->native_wl_hash, &wlid, img);
1127 glsym_evas_gl_common_image_free(img);
1128 free(n);
1129 return NULL;
1130 }
1131
1132 //XXX: workaround for mesa-10.2.8
1133 // mesa's eglQueryWaylandBufferWL() with EGL_WAYLAND_Y_INVERTED_WL works incorrect.
1134 //img->native.yinvert = yinvert;
1135 img->native.yinvert = 1;
1136 img->native.loose = 0;
1137 img->native.data = n;
1138 img->native.func.data = re;
1139 img->native.func.bind = _native_cb_bind;
1140 img->native.func.unbind = _native_cb_unbind;
1141 img->native.func.free = _native_cb_free;
1142 img->native.target = GL_TEXTURE_2D;
1143 img->native.mipmap = 0;
1144
1145 glsym_evas_gl_common_image_native_enable(img);
1146 }
1147 }
1148 }
1149 else if (ns->type == EVAS_NATIVE_SURFACE_OPENGL)
1150 {
1151 if (native)
1152 {
1153 if ((n = calloc(1, sizeof(Native))))
1154 {
1155 memcpy(&(n->ns), ns, sizeof(Evas_Native_Surface));
1156 eina_hash_add(ob->gl_context->shared->native_tex_hash, &texid, img);
1157
1158 n->egl_surface = 0;
1159
1160 img->native.yinvert = 0;
1161 img->native.loose = 0;
1162 img->native.data = n;
1163 img->native.func.data = re;
1164 img->native.func.bind = _native_cb_bind;
1165 img->native.func.unbind = _native_cb_unbind;
1166 img->native.func.free = _native_cb_free;
1167 img->native.target = GL_TEXTURE_2D;
1168 img->native.mipmap = 0;
1169
1170 glsym_evas_gl_common_image_native_enable(img);
1171 }
1172 }
1173 }
1174
1175 return img;
1176}
1177
1178
856/* module api functions */ 1179/* module api functions */
857static int 1180static int
858module_open(Evas_Module *em) 1181module_open(Evas_Module *em)
@@ -888,6 +1211,7 @@ module_open(Evas_Module *em)
888 ORD(canvas_alpha_get); 1211 ORD(canvas_alpha_get);
889 ORD(output_free); 1212 ORD(output_free);
890 ORD(output_dump); 1213 ORD(output_dump);
1214 ORD(image_native_set);
891 1215
892 /* Mesa's EGL driver loads wayland egl by default. (called by eglGetProcaddr() ) 1216 /* Mesa's EGL driver loads wayland egl by default. (called by eglGetProcaddr() )
893 * implicit env set (EGL_PLATFORM=drm) prevent that. */ 1217 * implicit env set (EGL_PLATFORM=drm) prevent that. */