EGong

git clone git://xatko.vsos.ethz.ch/EGong.git
Log | Files | Refs

Interfaces.c (6803B)


      1 #include <EGong/CNC.h>
      2 #include <EGong/Util/Dependencies.h>
      3 #include <EGong/Interfaces/STDIO.h>
      4 #include <EGong/Interfaces/CMD.h>
      5 #include <EGong/Util/Waiter.h>
      6 #include <EGong/Main.h>
      7 #include <EGong/Util/Config.h>
      8 #ifdef USE_GTK
      9 	#include <EGong/Interfaces/GTK.h>
     10 #endif
     11 #ifdef USE_AO
     12 	#include <EGong/Interfaces/Audio.h>
     13 #endif
     14 #ifdef USE_WINGUI
     15 	#include <EGong/Interfaces/Windows.h>
     16 #endif
     17 #if defined(USE_GTK) || defined(USE_WINGUI)
     18 	#include <EGong/Interfaces/GUI.h>
     19 #endif
     20 #include <EGong/Util/Log.h>
     21 #include <EGong/Util/Misc.h>
     22 #include <stdlib.h>
     23 
     24 struct EGong_interface EGong_interfaces[]={
     25 	{
     26 		.name="CMD", 
     27 		.identifier='C', 
     28 		.requirements=EGONG_DEP_NONE,
     29 		.state=EGONG_INTERFACE_ACTIVE, 
     30 		.funcs=&(struct EGong_if_ptrtbl){
     31 			.setup=&EGong_if_cmd_setup, 
     32 			.cycle=&EGong_if_cmd_cycle,
     33 			.display=NULL, 
     34 			.shutdown=NULL,
     35 			.sock_watch=NULL,
     36 			.loop=NULL,
     37 		}
     38 	},
     39 	#if defined(USE_GTK) || defined(USE_WINGUI)
     40 	{
     41 		.name="GUI", 
     42 		.identifier='G', 
     43 		.requirements=EGONG_DEP_LISTENER,
     44 		.state=0,
     45 		.funcs=&(struct EGong_if_ptrtbl){
     46 			.setup=&EGong_if_gui_setup, 
     47 			.cycle=&EGong_if_gui_cycle, 
     48 			.display=&EGong_if_gui_display, 
     49 			.shutdown=&EGong_if_gui_shutdown,
     50 			.sock_watch=&EGong_if_gui_sockwatch,
     51 			.loop=&EGong_if_gui_loop,
     52 		}
     53 	},
     54 	#endif
     55 	{
     56 		.name="STDIO", 
     57 		.identifier='S', 
     58 		.requirements=EGONG_DEP_LISTENER,
     59 		.state=0,
     60 		.funcs=&(struct EGong_if_ptrtbl){
     61 			.setup=&EGong_if_stdio_setup, 
     62 			.cycle=&EGong_if_stdio_cycle, 
     63 			.display=&EGong_if_stdio_display, 
     64 			.shutdown=NULL,
     65 			.sock_watch=NULL,
     66 			.loop=NULL,
     67 		}
     68 	},
     69 	#ifdef USE_AO
     70 	{
     71 		.name="Audio", 
     72 		.identifier='A', 
     73 		.requirements=EGONG_DEP_LISTENER,
     74 		.state=0,
     75 		.funcs=&(struct EGong_if_ptrtbl){
     76 			.setup=&EGong_if_audio_setup, 
     77 			.cycle=NULL, 
     78 			.display=&EGong_if_audio_display, 
     79 			.shutdown=&EGong_if_audio_shutdown
     80 			.sock_watch=NULL,
     81 			.loop=NULL,
     82 		}
     83 	}
     84 	#endif
     85 };
     86 unsigned short int EGong_interfaces_global_init_done=0;
     87 unsigned short int EGong_interfaces_userstreams=0;
     88 unsigned int EGong_interfaces_requirements=0;
     89 unsigned int EGong_interfaces_requirement_mask=0;
     90 
     91 unsigned short int EGong_interface_if_count_ustream(struct EGong_interface *interface){
     92 	unsigned short int streams=0;
     93 	if(interface->funcs->display!=NULL){
     94 		streams++;
     95 	}
     96 	if(interface->funcs->cycle!=NULL){
     97 		streams++;
     98 	}
     99 	return streams;
    100 }
    101 int EGong_interface_setup(struct EGong_interface *interface){
    102 	
    103 	if(!IF_CAN_SETUP(*interface)||!IF_ACTIVE(*interface)){
    104 		return EGONG_INTERFACE_RETURN_OK;
    105 	}
    106 	if(interface->funcs->sock_watch!=NULL){
    107 		EGong_waiter_add=interface->funcs->sock_watch;
    108 	}
    109 	if(interface->funcs->loop!=NULL){
    110 		Egong_main_loop_ptr=interface->funcs->loop;
    111 	}
    112 	if(interface->funcs->setup(interface)<0){
    113 		do_log_call_composite(LOG_COMPOSE_SRC, LOG_TYPE_NORMAL, LOG_LEVEL_ERROR, EGong_global_configuration.log.destinations, "Couldn't setup interface ", interface->name, NULL);
    114 		interface->state&=~(EGONG_INTERFACE_ACTIVE|EGONG_INTERFACE_SETUP);
    115 		return EGONG_INTERFACE_RETURN_ERROR;
    116 	}
    117 	if(EGong_deps_init(interface->requirements)>0){
    118 		do_log_call_composite(LOG_COMPOSE_SRC, LOG_TYPE_NORMAL, LOG_LEVEL_ERROR, EGong_global_configuration.log.destinations, "Couldn't setup interface ", interface->name, " due to unmet dependencies", NULL);
    119 		interface->state&=~(EGONG_INTERFACE_ACTIVE|EGONG_INTERFACE_SETUP);
    120 		return EGONG_INTERFACE_RETURN_ERROR;
    121 	}
    122 	interface->state|=EGONG_INTERFACE_SETUP;
    123 	EGong_interfaces_userstreams+=EGong_interface_if_count_ustream(interface);
    124 	return EGONG_INTERFACE_RETURN_OK;
    125 }
    126 int EGong_interface_activate(struct EGong_interface *interface){
    127 	if(EGong_interfaces_global_init_done==1&&!IF_TRY_SETUP(*interface)){
    128 		return -1;
    129 	}
    130 	if((interface->state&EGONG_INTERFACE_ACTIVE)>0){
    131 		return 1;
    132 	}
    133 	interface->state|=EGONG_INTERFACE_ACTIVE;
    134 	EGong_interfaces_userstreams+=EGong_interface_if_count_ustream(interface);
    135 	return 0;
    136 }
    137 int EGong_interface_shutdown(struct EGong_interface *interface){
    138 	if((interface->state&EGONG_INTERFACE_SETUP)>0){
    139 		return 1;
    140 	}
    141 	int ret=0;
    142 	if(interface->funcs->shutdown(interface)<0){
    143 		do_log_call_composite(LOG_COMPOSE_SRC, LOG_TYPE_NORMAL, LOG_LEVEL_ERROR, EGong_global_configuration.log.destinations, "Couldn't shutdown interface ", interface->name, NULL);
    144 		ret=EGONG_INTERFACE_RETURN_ERROR;
    145 	}
    146 	interface->state&=~EGONG_INTERFACE_SETUP;
    147 	EGong_interface_deactivate(interface);
    148 	return ret;
    149 }
    150 int EGong_interface_deactivate(struct EGong_interface *interface){
    151 	if(!IF_ACTIVE(*interface)){
    152 		return EGONG_INTERFACE_RETURN_OK;
    153 	}
    154 	interface->state&=~EGONG_INTERFACE_ACTIVE;
    155 	EGong_interfaces_userstreams-=EGong_interface_if_count_ustream(interface);
    156 	return 0;
    157 }
    158 struct EGong_interface *EGong_interface_get_from_id(char identifier){
    159 	int i;
    160 	for(i=0; i<CSIZEOF(EGong_interfaces); i++){
    161 		if(EGong_interfaces[i].identifier==identifier){
    162 			return &EGong_interfaces[i];
    163 		}
    164 	}
    165 	return NULL;
    166 }
    167 int EGong_interface_init(unsigned int requirement_mask){
    168 	do_log("Initializing interfaces", LOG_TYPE_NORMAL, LOG_LEVEL_DEBUG);
    169 	EGong_interfaces_requirement_mask=requirement_mask;
    170 	int i, ret;
    171 	for(i=0; i<CSIZEOF(EGong_interfaces); i++){
    172 		ret=EGong_interface_setup(&EGong_interfaces[i]);
    173 		EGONG_INTERFACE_INTERPRET_RET(ret, EGong_interfaces[i]);
    174 	}
    175 	if(EGong_interfaces_userstreams==0){
    176 		do_log("No userstreams available", LOG_TYPE_NORMAL, LOG_LEVEL_FATAL);
    177 		return -1;
    178 	}
    179 	EGong_interfaces_global_init_done=1;
    180 	do_log("Interfaces initialized", LOG_TYPE_NORMAL, LOG_LEVEL_DEBUG);
    181 	return 0;
    182 }
    183 int EGong_interface_cycle(void){
    184 	if(EGong_interfaces_userstreams==0){
    185 		do_log("No userstreams found, exiting...", LOG_TYPE_NORMAL, LOG_LEVEL_INFO);
    186 		return 1;
    187 	}
    188 	int i, ret;
    189 	String msg;
    190 	char *dest;
    191 	for(i=0; i<CSIZEOF(EGong_interfaces); i++){
    192 		if(IF_ACTIVE(EGong_interfaces[i]) && IF_CAN_CYCLE(EGong_interfaces[i])){
    193 			msg.data=dest=NULL; msg.length=0;
    194 			ret=EGong_interfaces[i].funcs->cycle(&EGong_interfaces[i], &msg, &dest);
    195 			EGONG_INTERFACE_INTERPRET_RET(ret, EGong_interfaces[i]);
    196 			if(msg.data!=NULL){
    197 				EGong_cnc_sendmessage(&msg, dest);
    198 				free(msg.data);
    199 			}
    200 		}
    201 	}
    202 	msg.data=NULL; msg.length=0;
    203 	if(DEP_AVAIL(EGONG_DEP_LISTENER)&&EGong_cnc_getmessage(&msg)==0){
    204 		for(i=0; i<CSIZEOF(EGong_interfaces); i++){
    205 			if(IF_ACTIVE(EGong_interfaces[i])&&IF_CAN_DISPLAY(EGong_interfaces[i])){
    206 				ret=EGong_interfaces[i].funcs->display(&EGong_interfaces[i],&msg);
    207 				EGONG_INTERFACE_INTERPRET_RET(ret, EGong_interfaces[i]);
    208 			}
    209 		}
    210 	}
    211 	if(msg.data!=NULL){
    212 		EGong_cnc_freemessage(&msg);
    213 	}
    214 	return 0;
    215 }
    216 
    217 int EGong_interface_deinit(void){
    218 	int i, ret;
    219 	for(i=0; i<sizeof(EGong_interfaces)/sizeof(*EGong_interfaces); i++){
    220 		if(IF_SETUP(EGong_interfaces[i])&&IF_CAN_SHUTDOWN(EGong_interfaces[i])){
    221 			ret=EGong_interface_shutdown(&EGong_interfaces[i]);
    222 			EGONG_INTERFACE_INTERPRET_RET(ret, EGong_interfaces[i]);
    223 		}
    224 	}
    225 }