2 * vim:ts=8:sw=3:sts=8:noexpandtab:cino=>5n-3f0^-2{2
10 #include "ecore_private.h"
11 #include "Ecore_Con.h"
12 #include "ecore_ipc_private.h"
13 #include "Ecore_Ipc.h"
15 #ifdef HAVE_NETINET_IN_H
16 # include <netinet/in.h>
19 #ifdef HAVE_WINSOCK2_H
20 # include <winsock2.h>
40 int _ecore_ipc_log_dom = -1;
42 /* byte swappers - for dealing with big vs little endian machines */
44 _ecore_ipc_swap_16(unsigned short v)
48 s = (unsigned char *)(&v);
49 t = s[0]; s[0] = s[1]; s[1] = t;
54 _ecore_ipc_swap_32(unsigned int v)
58 s = (unsigned char *)(&v);
59 t = s[0]; s[0] = s[3]; s[3] = t;
60 t = s[1]; s[1] = s[2]; s[2] = t;
64 EAPI unsigned long long
65 _ecore_ipc_swap_64(unsigned long long v)
69 s = (unsigned char *)(&v);
70 t = s[0]; s[0] = s[7]; s[7] = t;
71 t = s[1]; s[1] = s[6]; s[6] = t;
72 t = s[2]; s[2] = s[5]; s[5] = t;
73 t = s[3]; s[3] = s[4]; s[4] = t;
77 static int _ecore_ipc_dlt_int(int out, int prev, int *mode);
78 static int _ecore_ipc_ddlt_int(int in, int prev, int mode);
81 _ecore_ipc_dlt_int(int out, int prev, int *mode)
91 if (out == (int)0xffffffff)
101 if (out == prev << 1)
106 if (out == prev >> 1)
113 if (!(dlt & 0xffffff00))
119 if (!(dlt & 0xffffff00))
125 if (!(dlt & 0x00ffffff))
128 return (dlt >> 24) & 0xff;
131 if (!(dlt & 0x00ffffff))
134 return (dlt >> 24) & 0xff;
138 if (!(dlt & 0xffff0000))
144 if (!(dlt & 0xffff0000))
150 if (!(dlt & 0x0000ffff))
153 return (dlt >> 16) & 0xffff;
156 if (!(dlt & 0x0000ffff))
159 return (dlt >> 16) & 0xffff;
167 _ecore_ipc_ddlt_int(int in, int prev, int mode)
193 return prev + (in << 24);
196 return prev - (in << 24);
205 return prev + (in << 16);
208 return prev - (in << 16);
225 static int _ecore_ipc_event_client_add(void *data, int ev_type, void *ev);
226 static int _ecore_ipc_event_client_del(void *data, int ev_type, void *ev);
227 static int _ecore_ipc_event_server_add(void *data, int ev_type, void *ev);
228 static int _ecore_ipc_event_server_del(void *data, int ev_type, void *ev);
229 static int _ecore_ipc_event_client_data(void *data, int ev_type, void *ev);
230 static int _ecore_ipc_event_server_data(void *data, int ev_type, void *ev);
231 static void _ecore_ipc_event_client_add_free(void *data, void *ev);
232 static void _ecore_ipc_event_client_del_free(void *data, void *ev);
233 static void _ecore_ipc_event_client_data_free(void *data, void *ev);
234 static void _ecore_ipc_event_server_add_free(void *data, void *ev);
235 static void _ecore_ipc_event_server_del_free(void *data, void *ev);
236 static void _ecore_ipc_event_server_data_free(void *data, void *ev);
238 EAPI int ECORE_IPC_EVENT_CLIENT_ADD = 0;
239 EAPI int ECORE_IPC_EVENT_CLIENT_DEL = 0;
240 EAPI int ECORE_IPC_EVENT_SERVER_ADD = 0;
241 EAPI int ECORE_IPC_EVENT_SERVER_DEL = 0;
242 EAPI int ECORE_IPC_EVENT_CLIENT_DATA = 0;
243 EAPI int ECORE_IPC_EVENT_SERVER_DATA = 0;
245 static int _ecore_ipc_init_count = 0;
246 static Eina_List *servers = NULL;
247 static Ecore_Event_Handler *handler[6];
250 * @defgroup Ecore_IPC_Library_Group IPC Library Functions
252 * Functions that set up and shut down the Ecore IPC Library.
256 * Initialises the Ecore IPC library.
257 * @return Number of times the library has been initialised without
259 * @ingroup Ecore_IPC_Library_Group
266 if (++_ecore_ipc_init_count != 1)
267 return _ecore_ipc_init_count;
268 _ecore_ipc_log_dom = eina_log_domain_register("EcoreIpc", ECORE_DEFAULT_LOG_COLOR);
269 if(_ecore_ipc_log_dom < 0)
271 EINA_LOG_ERR("Impossible to create a log domain for the Ecore IPC module.");
272 return --_ecore_ipc_init_count;
274 if (!ecore_con_init())
275 return --_ecore_ipc_init_count;
277 ECORE_IPC_EVENT_CLIENT_ADD = ecore_event_type_new();
278 ECORE_IPC_EVENT_CLIENT_DEL = ecore_event_type_new();
279 ECORE_IPC_EVENT_SERVER_ADD = ecore_event_type_new();
280 ECORE_IPC_EVENT_SERVER_DEL = ecore_event_type_new();
281 ECORE_IPC_EVENT_CLIENT_DATA = ecore_event_type_new();
282 ECORE_IPC_EVENT_SERVER_DATA = ecore_event_type_new();
284 handler[i++] = ecore_event_handler_add(ECORE_CON_EVENT_CLIENT_ADD,
285 _ecore_ipc_event_client_add, NULL);
286 handler[i++] = ecore_event_handler_add(ECORE_CON_EVENT_CLIENT_DEL,
287 _ecore_ipc_event_client_del, NULL);
288 handler[i++] = ecore_event_handler_add(ECORE_CON_EVENT_SERVER_ADD,
289 _ecore_ipc_event_server_add, NULL);
290 handler[i++] = ecore_event_handler_add(ECORE_CON_EVENT_SERVER_DEL,
291 _ecore_ipc_event_server_del, NULL);
292 handler[i++] = ecore_event_handler_add(ECORE_CON_EVENT_CLIENT_DATA,
293 _ecore_ipc_event_client_data, NULL);
294 handler[i] = ecore_event_handler_add(ECORE_CON_EVENT_SERVER_DATA,
295 _ecore_ipc_event_server_data, NULL);
296 return _ecore_ipc_init_count;
300 * Shuts down the Ecore IPC library.
301 * @return Number of times the library has been initialised without being
303 * @ingroup Ecore_IPC_Library_Group
306 ecore_ipc_shutdown(void)
310 if (--_ecore_ipc_init_count != 0)
311 return _ecore_ipc_init_count;
313 while (servers) ecore_ipc_server_del(eina_list_data_get(servers));
315 for (i = 0; i < 6; i++)
316 ecore_event_handler_del(handler[i]);
318 ecore_con_shutdown();
319 eina_log_domain_unregister(_ecore_ipc_log_dom);
320 _ecore_ipc_log_dom = -1;
321 return _ecore_ipc_init_count;
325 * @defgroup Ecore_IPC_Server_Group IPC Server Functions
327 * Functions the deal with IPC server objects.
331 * Creates an IPC server that listens for connections.
333 * For more details about the @p compl_type, @p name and @p port
334 * parameters, see the @ref ecore_con_server_add documentation.
336 * @param compl_type The connection type.
337 * @param name Name to associate with the socket used for connection.
338 * @param port Number to identify with socket used for connection.
339 * @param data Data to associate with the IPC server.
340 * @return New IPC server. If there is an error, @c NULL is returned.
341 * @ingroup Ecore_IPC_Server_Group
342 * @todo Need to add protocol type parameter to this function.
344 EAPI Ecore_Ipc_Server *
345 ecore_ipc_server_add(Ecore_Ipc_Type compl_type, const char *name, int port, const void *data)
347 Ecore_Ipc_Server *svr;
349 Ecore_Con_Type extra = 0;
351 svr = calloc(1, sizeof(Ecore_Ipc_Server));
352 if (!svr) return NULL;
354 type &= ~ECORE_IPC_USE_SSL;
355 if (compl_type & ECORE_IPC_USE_SSL) extra = ECORE_CON_USE_SSL;
358 case ECORE_IPC_LOCAL_USER:
359 svr->server = ecore_con_server_add(ECORE_CON_LOCAL_USER | extra, name, port, svr);
361 case ECORE_IPC_LOCAL_SYSTEM:
362 svr->server = ecore_con_server_add(ECORE_CON_LOCAL_SYSTEM | extra, name, port, svr);
364 case ECORE_IPC_REMOTE_SYSTEM:
365 svr->server = ecore_con_server_add(ECORE_CON_REMOTE_SYSTEM | extra, name, port, svr);
376 svr->max_buf_size = 32 * 1024;
377 svr->data = (void *)data;
378 servers = eina_list_append(servers, svr);
379 ECORE_MAGIC_SET(svr, ECORE_MAGIC_IPC_SERVER);
384 * Creates an IPC server object to represent the IPC server listening
387 * For more details about the @p compl_type, @p name and @p port
388 * parameters, see the @ref ecore_con_server_connect documentation.
390 * @param compl_type The IPC connection type.
391 * @param name Name used to determine which socket to use for the
393 * @param port Number used to identify the socket to use for the
395 * @param data Data to associate with the server.
396 * @return A new IPC server. @c NULL is returned on error.
397 * @ingroup Ecore_IPC_Server_Group
398 * @todo Need to add protocol type parameter.
400 EAPI Ecore_Ipc_Server *
401 ecore_ipc_server_connect(Ecore_Ipc_Type compl_type, char *name, int port, const void *data)
403 Ecore_Ipc_Server *svr;
405 Ecore_Con_Type extra = 0;
407 svr = calloc(1, sizeof(Ecore_Ipc_Server));
408 if (!svr) return NULL;
410 type &= ~ECORE_IPC_USE_SSL;
411 if (compl_type & ECORE_IPC_USE_SSL) extra = ECORE_CON_USE_SSL;
414 case ECORE_IPC_LOCAL_USER:
415 svr->server = ecore_con_server_connect(ECORE_CON_LOCAL_USER | extra, name, port, svr);
417 case ECORE_IPC_LOCAL_SYSTEM:
418 svr->server = ecore_con_server_connect(ECORE_CON_LOCAL_SYSTEM | extra, name, port, svr);
420 case ECORE_IPC_REMOTE_SYSTEM:
421 svr->server = ecore_con_server_connect(ECORE_CON_REMOTE_SYSTEM | extra, name, port, svr);
432 svr->max_buf_size = -1;
433 svr->data = (void *)data;
434 servers = eina_list_append(servers, svr);
435 ECORE_MAGIC_SET(svr, ECORE_MAGIC_IPC_SERVER);
440 * Closes the connection and frees the given IPC server.
441 * @param svr The given IPC server.
442 * @return The data associated with the server when it was created.
443 * @ingroup Ecore_IPC_Server_Group
446 ecore_ipc_server_del(Ecore_Ipc_Server *svr)
450 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
452 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
453 "ecore_ipc_server_del");
456 if (svr->delete_me) return NULL;
461 if (svr->event_count == 0)
463 Ecore_Ipc_Client *cl;
465 EINA_LIST_FREE(svr->clients, cl)
466 ecore_ipc_client_del(cl);
467 ecore_con_server_del(svr->server);
468 servers = eina_list_remove(servers, svr);
470 if (svr->buf) free(svr->buf);
471 ECORE_MAGIC_SET(svr, ECORE_MAGIC_NONE);
478 * Retrieves the data associated with the given IPC server.
479 * @param svr The given IPC server.
480 * @return The associated data.
481 * @ingroup Ecore_IPC_Server_Group
484 ecore_ipc_server_data_get(Ecore_Ipc_Server *svr)
486 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
488 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
489 "ecore_ipc_server_data_get");
496 * Retrieves whether the given IPC server is currently connected.
497 * @param svr The given IPC server.
498 * @return @c 1 if the server is connected. @c 0 otherwise.
499 * @ingroup Ecore_IPC_Server_Group
502 ecore_ipc_server_connected_get(Ecore_Ipc_Server *svr)
504 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
506 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
507 "ecore_ipc_server_connected_get");
510 return ecore_con_server_connected_get(svr->server);
514 * Retrieves the list of clients for this server.
515 * @param svr The given IPC server.
516 * @return An Eina_List with the clients.
517 * @ingroup Ecore_IPC_Server_Group
520 ecore_ipc_server_clients_get(Ecore_Ipc_Server *svr)
522 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
524 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
525 "ecore_ipc_server_clients_get");
528 return svr->client_list;
531 #define SVENC(_member) \
532 d = _ecore_ipc_dlt_int(msg._member, svr->prev.o._member, &md); \
537 dd = (unsigned char *)&v; \
540 *(dat + s + 0) = dd[0]; \
541 *(dat + s + 1) = dd[1]; \
542 *(dat + s + 2) = dd[2]; \
543 *(dat + s + 3) = dd[3]; \
546 else if (md >= DLT_ADD16) \
550 dd = (unsigned char *)&v; \
553 *(dat + s + 0) = dd[0]; \
554 *(dat + s + 1) = dd[1]; \
557 else if (md >= DLT_ADD8) \
559 *(dat + s + 0) = (unsigned char)d; \
564 * Sends a message to the given IPC server.
566 * The content of the parameters, excluding the @p svr paramter, is up to
569 * @param svr The given IPC server.
570 * @param major Major opcode of the message.
571 * @param minor Minor opcode of the message.
572 * @param ref Message reference number.
573 * @param ref_to Reference number of the message this message refers to.
574 * @param response Requires response.
575 * @param data The data to send as part of the message.
576 * @param size Length of the data, in bytes, to send.
577 * @return Number of bytes sent. @c 0 is returned if there is an error.
578 * @ingroup Ecore_IPC_Server_Group
579 * @todo This function needs to become an IPC message.
580 * @todo Fix up the documentation: Make sure what ref_to and response are.
583 ecore_ipc_server_send(Ecore_Ipc_Server *svr, int major, int minor, int ref, int ref_to, int response, const void *data, int size)
585 Ecore_Ipc_Msg_Head msg;
587 int *head, md = 0, d, s;
588 unsigned char dat[sizeof(Ecore_Ipc_Msg_Head)];
590 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
592 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
593 "ecore_ipc_server_send");
596 if (size < 0) size = 0;
601 msg.response = response;
608 *head |= md << (4 * 1);
610 *head |= md << (4 * 2);
612 *head |= md << (4 * 3);
614 *head |= md << (4 * 4);
616 *head |= md << (4 * 5);
617 *head = htonl(*head);
619 ret = ecore_con_server_send(svr->server, dat, s);
620 if (size > 0) ret += ecore_con_server_send(svr->server, data, size);
625 * Sets a limit on the number of clients that can be handled concurrently
626 * by the given server, and a policy on what to do if excess clients try to
628 * Beware that if you set this once ecore is already running, you may
629 * already have pending CLIENT_ADD events in your event queue. Those
630 * clients have already connected and will not be affected by this call.
631 * Only clients subsequently trying to connect will be affected.
632 * @param svr The given server.
633 * @param client_limit The maximum number of clients to handle
634 * concurrently. -1 means unlimited (default). 0
635 * effectively disables the server.
636 * @param reject_excess_clients Set to 1 to automatically disconnect
637 * excess clients as soon as they connect if you are
638 * already handling client_limit clients. Set to 0
639 * (default) to just hold off on the "accept()"
640 * system call until the number of active clients
641 * drops. This causes the kernel to queue up to 4096
642 * connections (or your kernel's limit, whichever is
644 * @ingroup Ecore_Ipc_Server_Group
647 ecore_ipc_server_client_limit_set(Ecore_Ipc_Server *svr, int client_limit, char reject_excess_clients)
649 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
651 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
652 "ecore_ipc_server_client_limit_set");
655 ecore_con_server_client_limit_set(svr->server, client_limit, reject_excess_clients);
659 * Sets the max data payload size for an Ipc message in bytes
661 * @param svr The given server.
662 * @param size The maximum data payload size in bytes.
663 * @ingroup Ecore_Ipc_Server_Group
666 ecore_ipc_server_data_size_max_set(Ecore_Ipc_Server *svr, int size)
668 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
670 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
671 "ecore_ipc_server_data_size_max_set");
674 svr->max_buf_size = size;
678 * Gets the max data payload size for an Ipc message in bytes
680 * @param svr The given server.
681 * @return The maximum data payload in bytes.
682 * @ingroup Ecore_Ipc_Server_Group
685 ecore_ipc_server_data_size_max_get(Ecore_Ipc_Server *svr)
687 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
689 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
690 "ecore_ipc_server_data_size_max_get");
693 return svr->max_buf_size;
697 * Gets the IP address of a server that has been connected to.
699 * @param svr The given server.
700 * @return A pointer to an internal string that contains the IP address of
701 * the connected server in the form "XXX.YYY.ZZZ.AAA" IP notation.
702 * This string should not be modified or trusted to stay valid after
703 * deletion for the @p svr object. If no IP is known NULL is returned.
704 * @ingroup Ecore_Ipc_Server_Group
707 ecore_ipc_server_ip_get(Ecore_Ipc_Server *svr)
709 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
711 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
712 "ecore_ipc_server_ip_get");
715 return ecore_con_server_ip_get(svr->server);
719 * Flushes all pending data to the given server. Will return when done.
721 * @param svr The given server.
722 * @ingroup Ecore_Ipc_Server_Group
725 ecore_ipc_server_flush(Ecore_Ipc_Server *svr)
727 if (!ECORE_MAGIC_CHECK(svr, ECORE_MAGIC_IPC_SERVER))
729 ECORE_MAGIC_FAIL(svr, ECORE_MAGIC_IPC_SERVER,
730 "ecore_ipc_server_server_flush");
733 ecore_con_server_flush(svr->server);
736 #define CLENC(_member) \
737 d = _ecore_ipc_dlt_int(msg._member, cl->prev.o._member, &md); \
742 dd = (unsigned char *)&v; \
745 *(dat + s + 0) = dd[0]; \
746 *(dat + s + 1) = dd[1]; \
747 *(dat + s + 2) = dd[2]; \
748 *(dat + s + 3) = dd[3]; \
751 else if (md >= DLT_ADD16) \
755 dd = (unsigned char *)&v; \
758 *(dat + s + 0) = dd[0]; \
759 *(dat + s + 1) = dd[1]; \
762 else if (md >= DLT_ADD8) \
764 *(dat + s) = (unsigned char)d; \
769 * @defgroup Ecore_IPC_Client_Group IPC Client Functions
771 * Functions that deal with IPC client objects.
775 * Sends a message to the given IPC client.
776 * @param cl The given IPC client.
777 * @param major Major opcode of the message.
778 * @param minor Minor opcode of the message.
779 * @param ref Reference number of the message.
780 * @param ref_to Reference number of the message this message refers to.
781 * @param response Requires response.
782 * @param data The data to send as part of the message.
783 * @param size Length of the data, in bytes, to send.
784 * @return The number of bytes sent. @c 0 will be returned if there is
786 * @ingroup Ecore_IPC_Client_Group
787 * @todo This function needs to become an IPC message.
788 * @todo Make sure ref_to and response parameters are described correctly.
791 ecore_ipc_client_send(Ecore_Ipc_Client *cl, int major, int minor, int ref, int ref_to, int response, const void *data, int size)
793 Ecore_Ipc_Msg_Head msg;
795 int *head, md = 0, d, s;
796 unsigned char dat[sizeof(Ecore_Ipc_Msg_Head)];
798 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
800 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
801 "ecore_ipc_client_send");
804 if (size < 0) size = 0;
809 msg.response = response;
816 *head |= md << (4 * 1);
818 *head |= md << (4 * 2);
820 *head |= md << (4 * 3);
822 *head |= md << (4 * 4);
824 *head |= md << (4 * 5);
825 *head = htonl(*head);
827 ret = ecore_con_client_send(cl->client, dat, s);
828 if (size > 0) ret += ecore_con_client_send(cl->client, data, size);
833 * Retrieves the IPC server that the given IPC client is connected to.
834 * @param cl The given IPC client.
835 * @return The IPC server the IPC client is connected to.
836 * @ingroup Ecore_IPC_Client_Group
838 EAPI Ecore_Ipc_Server *
839 ecore_ipc_client_server_get(Ecore_Ipc_Client *cl)
841 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
843 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
844 "ecore_ipc_client_server_get");
847 return (ecore_con_server_data_get(ecore_con_client_server_get(cl->client)));
851 * Closes the connection and frees memory allocated to the given IPC
853 * @param cl The given client.
854 * @return Data associated with the client.
855 * @ingroup Ecore_IPC_Client_Group
858 ecore_ipc_client_del(Ecore_Ipc_Client *cl)
861 Ecore_Ipc_Server *svr;
863 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
865 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
866 "ecore_ipc_client_del");
872 if (cl->event_count == 0)
874 svr = ecore_con_server_data_get(ecore_con_client_server_get(cl->client));
875 ecore_con_client_del(cl->client);
876 svr->clients = eina_list_remove(svr->clients, cl);
877 if (cl->buf) free(cl->buf);
878 ECORE_MAGIC_SET(cl, ECORE_MAGIC_NONE);
885 * Sets the IPC data associated with the given IPC client to @p data.
886 * @param cl The given IPC client.
887 * @param data The data to associate with the IPC client.
888 * @ingroup Ecore_IPC_Client_Group
891 ecore_ipc_client_data_set(Ecore_Ipc_Client *cl, const void *data)
893 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
895 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
896 "ecore_ipc_client_data_set");
899 cl->data = (void *)data;
903 * Retrieves the data that has been associated with the given IPC client.
904 * @param cl The given client.
905 * @return The data associated with the IPC client.
906 * @ingroup Ecore_IPC_Client_Group
909 ecore_ipc_client_data_get(Ecore_Ipc_Client *cl)
911 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
913 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
914 "ecore_ipc_client_data_get");
921 * Sets the max data payload size for an Ipc message in bytes
923 * @param client The given client.
924 * @param size The maximum data payload size in bytes.
925 * @ingroup Ecore_Ipc_Client_Group
928 ecore_ipc_client_data_size_max_set(Ecore_Ipc_Client *cl, int size)
930 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
932 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
933 "ecore_ipc_client_data_size_max_set");
936 cl->max_buf_size = size;
940 * Sets the max data payload size for an Ipc message in bytes
942 * @param cl The given client.
943 * @param size The maximum data payload size in bytes.
944 * @ingroup Ecore_Ipc_Client_Group
947 ecore_ipc_client_data_size_max_get(Ecore_Ipc_Client *cl)
949 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
951 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
952 "ecore_ipc_client_data_size_max_get");
955 return cl->max_buf_size;
959 * Gets the IP address of a client that has been connected to.
961 * @param cl The given client.
962 * @return A pointer to an internal string that contains the IP address of
963 * the connected server in the form "XXX.YYY.ZZZ.AAA" IP notation.
964 * This string should not be modified or trusted to stay valid after
965 * deletion for the @p cl object. If no IP is known NULL is returned.
966 * @ingroup Ecore_Ipc_Client_Group
969 ecore_ipc_client_ip_get(Ecore_Ipc_Client *cl)
971 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
973 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
974 "ecore_ipc_client_ip_get");
977 return ecore_con_client_ip_get(cl->client);
981 * Flushes all pending data to the given client. Will return when done.
983 * @param cl The given client.
984 * @ingroup Ecore_Ipc_Client_Group
987 ecore_ipc_client_flush(Ecore_Ipc_Client *cl)
989 if (!ECORE_MAGIC_CHECK(cl, ECORE_MAGIC_IPC_CLIENT))
991 ECORE_MAGIC_FAIL(cl, ECORE_MAGIC_IPC_CLIENT,
992 "ecore_ipc_client_flush");
995 ecore_con_client_flush(cl->client);
999 * Returns if SSL support is available
1000 * @return 1 if SSL is available, 0 if it is not.
1001 * @ingroup Ecore_Con_Client_Group
1004 ecore_ipc_ssl_available_get(void)
1006 return ecore_con_ssl_available_get();
1011 _ecore_ipc_event_client_add(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1013 Ecore_Con_Event_Client_Add *e;
1016 if (!eina_list_data_find(servers, ecore_con_server_data_get(ecore_con_client_server_get(e->client)))) return 1;
1017 /* handling code here */
1019 Ecore_Ipc_Client *cl;
1020 Ecore_Ipc_Server *svr;
1022 cl = calloc(1, sizeof(Ecore_Ipc_Client));
1024 svr = ecore_con_server_data_get(ecore_con_client_server_get(e->client));
1025 ECORE_MAGIC_SET(cl, ECORE_MAGIC_IPC_CLIENT);
1026 cl->client = e->client;
1027 cl->max_buf_size = 32 * 1024;
1028 ecore_con_client_data_set(cl->client, (void *)cl);
1029 svr->clients = eina_list_append(svr->clients, cl);
1030 svr->client_list = eina_list_append(svr->client_list, cl);
1033 Ecore_Ipc_Event_Client_Add *e2;
1035 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Client_Add));
1040 ecore_event_add(ECORE_IPC_EVENT_CLIENT_ADD, e2,
1041 _ecore_ipc_event_client_add_free, NULL);
1049 _ecore_ipc_event_client_del(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1051 Ecore_Con_Event_Client_Del *e;
1054 if (!eina_list_data_find(servers, ecore_con_server_data_get(ecore_con_client_server_get(e->client)))) return 1;
1055 /* handling code here */
1057 Ecore_Ipc_Client *cl;
1059 cl = ecore_con_client_data_get(e->client);
1061 Ecore_Ipc_Event_Client_Del *e2;
1062 Ecore_Ipc_Server *svr;
1064 svr = ecore_con_server_data_get(ecore_con_client_server_get(e->client));
1065 svr->client_list = eina_list_remove(svr->client_list, cl);
1068 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Client_Del));
1073 ecore_event_add(ECORE_IPC_EVENT_CLIENT_DEL, e2,
1074 _ecore_ipc_event_client_del_free, NULL);
1083 _ecore_ipc_event_server_add(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1085 Ecore_Con_Event_Server_Add *e;
1088 if (!eina_list_data_find(servers, ecore_con_server_data_get(e->server))) return 1;
1089 /* handling code here */
1091 Ecore_Ipc_Server *svr;
1093 svr = ecore_con_server_data_get(e->server);
1094 if (!svr->delete_me)
1096 Ecore_Ipc_Event_Server_Add *e2;
1098 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Server_Add));
1103 ecore_event_add(ECORE_IPC_EVENT_SERVER_ADD, e2,
1104 _ecore_ipc_event_server_add_free, NULL);
1112 _ecore_ipc_event_server_del(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1114 Ecore_Con_Event_Server_Del *e;
1117 if (!eina_list_data_find(servers, ecore_con_server_data_get(e->server))) return 1;
1118 /* handling code here */
1120 Ecore_Ipc_Server *svr;
1122 svr = ecore_con_server_data_get(e->server);
1123 if (!svr->delete_me)
1125 Ecore_Ipc_Event_Server_Del *e2;
1127 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Server_Del));
1132 ecore_event_add(ECORE_IPC_EVENT_SERVER_DEL, e2,
1133 _ecore_ipc_event_server_del_free, NULL);
1141 md = ((head >> (4 * _n)) & 0xf); \
1142 if (md >= DLT_SET) s += 4; \
1143 else if (md >= DLT_ADD16) s += 2; \
1144 else if (md >= DLT_ADD8) s += 1;
1146 #define CLDEC(_n, _member) \
1147 md = ((head >> (4 * _n)) & 0xf); \
1148 if (md >= DLT_SET) \
1151 unsigned char *dv; \
1152 dv = (unsigned char *)&v; \
1153 dv[0] = *(cl->buf + offset + s + 0); \
1154 dv[1] = *(cl->buf + offset + s + 1); \
1155 dv[2] = *(cl->buf + offset + s + 2); \
1156 dv[3] = *(cl->buf + offset + s + 3); \
1157 d = (int)ntohl(v); \
1160 else if (md >= DLT_ADD16) \
1163 unsigned char *dv; \
1164 dv = (unsigned char *)&v; \
1165 dv[0] = *(cl->buf + offset + s + 0); \
1166 dv[1] = *(cl->buf + offset + s + 1); \
1167 d = (int)ntohs(v); \
1170 else if (md >= DLT_ADD8) \
1173 unsigned char *dv; \
1174 dv = (unsigned char *)&v; \
1175 dv[0] = *(cl->buf + offset + s + 0); \
1179 msg._member = _ecore_ipc_ddlt_int(d, cl->prev.i._member, md);
1182 _ecore_ipc_event_client_data(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1184 Ecore_Con_Event_Client_Data *e;
1187 if (!eina_list_data_find(servers, ecore_con_server_data_get(ecore_con_client_server_get(e->client)))) return 1;
1188 /* handling code here */
1190 Ecore_Ipc_Client *cl;
1191 Ecore_Ipc_Msg_Head msg;
1195 cl = ecore_con_client_data_get(e->client);
1199 cl->buf_size = e->size;
1201 e->data = NULL; /* take it out of the old event */
1205 buf = realloc(cl->buf, cl->buf_size + e->size);
1214 memcpy(cl->buf + cl->buf_size, e->data, e->size);
1215 cl->buf_size += e->size;
1217 /* examine header */
1219 if ((cl->buf_size - offset) >= (int)sizeof(int))
1221 int s, md, d = 0, head;
1224 dd = (unsigned char *)&head;
1225 dd[0] = *(cl->buf + offset + 0);
1226 dd[1] = *(cl->buf + offset + 1);
1227 dd[2] = *(cl->buf + offset + 2);
1228 dd[3] = *(cl->buf + offset + 3);
1230 dd = (unsigned char *)&d;
1238 if ((cl->buf_size - offset) < s)
1240 if (offset > 0) goto scroll;
1251 if (msg.size < 0) msg.size = 0;
1252 /* there is enough data in the buffer for a full message */
1253 if ((cl->buf_size - offset) >= (s + msg.size))
1255 Ecore_Ipc_Event_Client_Data *e2;
1256 Ecore_Ipc_Server *svr;
1260 svr = ecore_con_server_data_get(ecore_con_client_server_get(cl->client));
1261 max = svr->max_buf_size;
1262 max2 = cl->max_buf_size;
1263 if ((max >= 0) && (max2 >= 0))
1265 if (max2 < max) max = max2;
1269 if (max < 0) max = max2;
1271 if ((max < 0) || (msg.size <= max))
1275 buf = malloc(msg.size);
1277 memcpy(buf, cl->buf + offset + s, msg.size);
1281 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Client_Data));
1286 e2->major = msg.major;
1287 e2->minor = msg.minor;
1289 e2->ref_to = msg.ref_to;
1290 e2->response = msg.response;
1291 e2->size = msg.size;
1293 ecore_event_add(ECORE_IPC_EVENT_CLIENT_DATA, e2,
1294 _ecore_ipc_event_client_data_free,
1300 offset += (s + msg.size);
1301 if (cl->buf_size == offset)
1315 buf = malloc(cl->buf_size - offset);
1323 memcpy(buf, cl->buf + offset, cl->buf_size - offset);
1326 cl->buf_size -= offset;
1333 md = ((head >> (4 * _n)) & 0xf); \
1334 if (md >= DLT_SET) s += 4; \
1335 else if (md >= DLT_ADD16) s += 2; \
1336 else if (md >= DLT_ADD8) s += 1;
1338 #define SVDEC(_n, _member) \
1339 md = ((head >> (4 * _n)) & 0xf); \
1340 if (md >= DLT_SET) \
1343 unsigned char *dv; \
1344 dv = (unsigned char *)&v; \
1345 dv[0] = *(svr->buf + offset + s + 0); \
1346 dv[1] = *(svr->buf + offset + s + 1); \
1347 dv[2] = *(svr->buf + offset + s + 2); \
1348 dv[3] = *(svr->buf + offset + s + 3); \
1349 d = (int)ntohl(v); \
1352 else if (md >= DLT_ADD16) \
1355 unsigned char *dv; \
1356 dv = (unsigned char *)&v; \
1357 dv[0] = *(svr->buf + offset + s + 0); \
1358 dv[1] = *(svr->buf + offset + s + 1); \
1359 d = (int)ntohs(v); \
1362 else if (md >= DLT_ADD8) \
1365 unsigned char *dv; \
1366 dv = (unsigned char *)&v; \
1367 dv[0] = *(svr->buf + offset + s + 0); \
1371 msg._member = _ecore_ipc_ddlt_int(d, svr->prev.i._member, md);
1374 _ecore_ipc_event_server_data(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1376 Ecore_Con_Event_Server_Data *e;
1379 if (!eina_list_data_find(servers, ecore_con_server_data_get(e->server))) return 1;
1380 /* handling code here */
1382 Ecore_Ipc_Server *svr;
1383 Ecore_Ipc_Msg_Head msg;
1387 svr = ecore_con_server_data_get(e->server);
1391 svr->buf_size = e->size;
1393 e->data = NULL; /* take it out of the old event */
1397 buf = realloc(svr->buf, svr->buf_size + e->size);
1406 memcpy(svr->buf + svr->buf_size, e->data, e->size);
1407 svr->buf_size += e->size;
1409 /* examine header */
1411 if ((svr->buf_size - offset) >= (int)sizeof(int))
1413 int s, md, d = 0, head;
1416 dd = (unsigned char *)&head;
1417 dd[0] = *(svr->buf + offset + 0);
1418 dd[1] = *(svr->buf + offset + 1);
1419 dd[2] = *(svr->buf + offset + 2);
1420 dd[3] = *(svr->buf + offset + 3);
1422 dd = (unsigned char *)&d;
1430 if ((svr->buf_size - offset) < s)
1432 if (offset > 0) goto scroll;
1443 if (msg.size < 0) msg.size = 0;
1444 /* there is enough data in the buffer for a full message */
1445 if ((svr->buf_size - offset) >= (s + msg.size))
1447 Ecore_Ipc_Event_Server_Data *e2;
1451 max = svr->max_buf_size;
1452 if ((max < 0) || (msg.size <= max))
1456 buf = malloc(msg.size);
1458 memcpy(buf, svr->buf + offset + s, msg.size);
1460 if (!svr->delete_me)
1462 e2 = calloc(1, sizeof(Ecore_Ipc_Event_Server_Data));
1467 e2->major = msg.major;
1468 e2->minor = msg.minor;
1470 e2->ref_to = msg.ref_to;
1471 e2->response = msg.response;
1472 e2->size = msg.size;
1474 ecore_event_add(ECORE_IPC_EVENT_SERVER_DATA, e2,
1475 _ecore_ipc_event_server_data_free,
1481 offset += (s + msg.size);
1482 if (svr->buf_size == offset)
1496 buf = malloc(svr->buf_size - offset);
1504 memcpy(buf, svr->buf + offset, svr->buf_size - offset);
1507 svr->buf_size -= offset;
1514 _ecore_ipc_event_client_add_free(void *data __UNUSED__, void *ev)
1516 Ecore_Ipc_Event_Client_Add *e;
1519 e->client->event_count--;
1520 if ((e->client->event_count == 0) && (e->client->delete_me))
1521 ecore_ipc_client_del(e->client);
1526 _ecore_ipc_event_client_del_free(void *data __UNUSED__, void *ev)
1528 Ecore_Ipc_Event_Client_Del *e;
1531 e->client->event_count--;
1532 if ((e->client->event_count == 0) && (e->client->delete_me))
1533 ecore_ipc_client_del(e->client);
1538 _ecore_ipc_event_client_data_free(void *data __UNUSED__, void *ev)
1540 Ecore_Ipc_Event_Client_Data *e;
1543 e->client->event_count--;
1544 if (e->data) free(e->data);
1545 if ((e->client->event_count == 0) && (e->client->delete_me))
1546 ecore_ipc_client_del(e->client);
1551 _ecore_ipc_event_server_add_free(void *data __UNUSED__, void *ev)
1553 Ecore_Ipc_Event_Server_Add *e;
1556 e->server->event_count--;
1557 if ((e->server->event_count == 0) && (e->server->delete_me))
1558 ecore_ipc_server_del(e->server);
1563 _ecore_ipc_event_server_del_free(void *data __UNUSED__, void *ev)
1565 Ecore_Ipc_Event_Server_Add *e;
1568 e->server->event_count--;
1569 if ((e->server->event_count == 0) && (e->server->delete_me))
1570 ecore_ipc_server_del(e->server);
1575 _ecore_ipc_event_server_data_free(void *data __UNUSED__, void *ev)
1577 Ecore_Ipc_Event_Server_Data *e;
1580 if (e->data) free(e->data);
1581 e->server->event_count--;
1582 if ((e->server->event_count == 0) && (e->server->delete_me))
1583 ecore_ipc_server_del(e->server);