enlightenment/src/bin/e_remote_main.c

249 lines
5.5 KiB
C

/*
* vim:ts=8:sw=3:sts=8:noexpandtab:cino=>5n-3f0^-2{2
*/
#include "e.h"
#ifdef USE_IPC
typedef struct _Opt Opt;
struct _Opt
{
char *opt;
int num_param;
char *desc;
int num_reply;
E_Ipc_Op opcode;
};
Opt opts[] = {
#define TYPE E_REMOTE_OPTIONS
#include "e_ipc_handlers.h"
#undef TYPE
};
static int _e_cb_signal_exit(void *data, int ev_type, void *ev);
static int _e_ipc_init(void);
static void _e_ipc_shutdown(void);
static int _e_ipc_cb_server_add(void *data, int type, void *event);
static int _e_ipc_cb_server_del(void *data, int type, void *event);
static int _e_ipc_cb_server_data(void *data, int type, void *event);
static void _e_help(void);
/* local subsystem globals */
static Ecore_Ipc_Server *_e_ipc_server = NULL;
static const char *display_name = NULL;
static int reply_count = 0;
static int reply_expect = 0;
#endif
int
main(int argc, char **argv)
{
#ifdef USE_IPC
int i;
/* handle some command-line parameters */
display_name = (const char *)getenv("DISPLAY");
for (i = 1; i < argc; i++)
{
if ((!strcmp(argv[i], "-h")) ||
(!strcmp(argv[i], "-help")) ||
(!strcmp(argv[i], "--h")) ||
(!strcmp(argv[i], "--help")))
{
_e_help();
exit(0);
}
}
/* basic ecore init */
if (!ecore_init())
{
printf("ERROR: Enlightenment_remote cannot Initialize Ecore!\n"
"Perhaps you are out of memory?\n");
exit(-1);
}
ecore_app_args_set(argc, (const char **)argv);
/* setup a handler for when e is asked to exit via a system signal */
if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_EXIT, _e_cb_signal_exit, NULL))
{
printf("ERROR: Enlightenment_remote cannot set up an exit signal handler.\n"
"Perhaps you are out of memory?\n");
exit(-1);
}
/* init ipc */
if (!ecore_ipc_init())
{
printf("ERROR: Enlightenment_remote cannot initialize the ipc system.\n"
"Perhaps you are out of memory?\n");
exit(-1);
}
/* setup e ipc service */
if (!_e_ipc_init())
{
printf("ERROR: Enlightenment_remote cannot set up the IPC socket.\n"
"Maybe try the '-display :0.0' option?\n");
exit(-1);
}
e_ipc_codec_init();
/* start our main loop */
ecore_main_loop_begin();
e_ipc_codec_shutdown();
_e_ipc_shutdown();
ecore_ipc_shutdown();
ecore_shutdown();
#endif
/* just return 0 to keep the compiler quiet */
return 0;
}
#ifdef USE_IPC
/* local subsystem functions */
static int
_e_cb_signal_exit(void *data, int ev_type, void *ev)
{
/* called on ctrl-c, kill (pid) (also SIGINT, SIGTERM and SIGQIT) */
ecore_main_loop_quit();
return 1;
}
static int
_e_ipc_init(void)
{
char *sdir;
sdir = getenv("E_IPC_SOCKET");
if (!sdir)
{
printf("The E_IPC_SOCKET environment variable is not set. This is\n"
"exported by Enlightenment to all processes it launches.\n"
"This environment variable must be set and must point to\n"
"Enlightenment's IPC socket file (minus port number).\n");
return 0;
}
_e_ipc_server = ecore_ipc_server_connect(ECORE_IPC_LOCAL_SYSTEM, sdir, 0, NULL);
if (!_e_ipc_server) return 0;
ecore_event_handler_add(ECORE_IPC_EVENT_SERVER_ADD, _e_ipc_cb_server_add, NULL);
ecore_event_handler_add(ECORE_IPC_EVENT_SERVER_DEL, _e_ipc_cb_server_del, NULL);
ecore_event_handler_add(ECORE_IPC_EVENT_SERVER_DATA, _e_ipc_cb_server_data, NULL);
return 1;
}
static void
_e_ipc_shutdown(void)
{
if (_e_ipc_server)
{
ecore_ipc_server_del(_e_ipc_server);
_e_ipc_server = NULL;
}
}
static int
_e_ipc_cb_server_add(void *data, int type, void *event)
{
Ecore_Ipc_Event_Server_Add *e;
char **argv, **params;
int i, j, argc, process_count = 0;
e = event;
ecore_app_args_get(&argc, &argv);
for (i = 1; i < argc; i++)
{
for (j = 0; j < (int)(sizeof(opts) / sizeof(Opt)); j++)
{
Opt *opt;
opt = &(opts[j]);
if (!strcmp(opt->opt, argv[i]))
{
if (i >= (argc - opt->num_param))
{
printf("ERROR: option %s expects %i parameters\n",
opt->opt, opt->num_param);
exit(-1);
}
else
{
params = &(argv[i + 1]);
switch (opt->opcode)
{
#define TYPE E_REMOTE_OUT
#include "e_ipc_handlers.h"
#undef TYPE
default:
break;
}
process_count++;
reply_expect += opt->num_reply;
i += opt->num_param;
}
}
}
}
if (process_count <= 0) _e_help();
if (reply_count >= reply_expect) ecore_main_loop_quit();
return 1;
}
static int
_e_ipc_cb_server_del(void *data, int type, void *event)
{
Ecore_Ipc_Event_Server_Del *e;
e = event;
return 1;
}
static int
_e_ipc_cb_server_data(void *data, int type, void *event)
{
Ecore_Ipc_Event_Server_Data *e;
e = event;
printf("REPLY <- BEGIN\n");
switch (e->minor)
{
#define TYPE E_REMOTE_IN
#include "e_ipc_handlers.h"
#undef TYPE
default:
break;
}
printf("REPLY <- END\n");
reply_count++;
if (reply_count >= reply_expect) ecore_main_loop_quit();
return 1;
}
static void
_e_help(void)
{
int i, j;
printf("OPTIONS:\n");
printf(" -h This help\n");
printf(" -help This help\n");
printf(" --help This help\n");
printf(" --h This help\n");
for (j = 0; j < (int)(sizeof(opts) / sizeof(Opt)); j++)
{
Opt *opt;
opt = &(opts[j]);
printf(" %s ", opt->opt);
for (i = 0; i < opt->num_param; i++)
printf("OPT%i ", i + 1);
printf("%s\n", opt->desc);
}
}
#endif