⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 client.c

📁 系统任务管理器
💻 C
📖 第 1 页 / 共 3 页
字号:
	{	struct tm	*t;	t = &server_time;	sscanf(s, "%d %d %d %d %d %d %d %d %d",			&t->tm_sec, &t->tm_min, &t->tm_hour,			&t->tm_mday, &t->tm_mon, &t->tm_year,			&t->tm_wday, &t->tm_yday, &t->tm_isdst);	}/* ================================================================= */static voidclient_server_version_setup(gchar *line)	{	sscanf(line, "%*s %d.%d.%d", &server_major_version,                    &server_minor_version, &server_rev_version);	}static voidclient_hostname_setup(gchar *s)	{	g_free(_GK.server_hostname);	_GK.server_hostname = g_strdup(s);	}static voidclient_sysname_setup(gchar *s)	{	g_free(_GK.server_sysname);	_GK.server_sysname = g_strdup(s);	}KeyTable	monitor_table[] =	{	{"sensors",		client_sys_sensors_init },	{"cpu",			client_sys_cpu_init },	{"proc",		client_sys_proc_init },	{"disk",		client_sys_disk_init },	{"net",			client_sys_net_init },	{"inet",		client_sys_inet_init },	{"mem",			client_sys_mem_init },	{"fs",			client_sys_fs_init },	{"mail",		client_sys_mail_init },	{"apm",			client_sys_battery_init },	{"battery",		client_sys_battery_init },	{"uptime",		client_sys_uptime_init },	};static gboolean	setup_done;		/* only one sys init */  /* Setup lines are received before monitor init functions are called, so  |  for plugins must save the strings until plugins are loaded.  */static GList	*client_plugin_setup_line_list;static voidclient_plugin_add_setup_line(gchar *line)	{	client_plugin_setup_line_list				= g_list_append(client_plugin_setup_line_list, g_strdup(line));	}  /* Plugins should call this in their gkrellm_init_plugin() function.  */voidgkrellm_client_plugin_get_setup(gchar *key_name,				void (*setup_func_cb)(gchar *str))	{	GList	*list;	gchar	*line, *s;	gint	n;	if (!_GK.client_mode || !key_name || !setup_func_cb)		return;	for (list = client_plugin_setup_line_list; list; list = list->next)		{		line = (gchar *) list->data;		n = strlen(key_name);		s = line + n;		if (!strncmp(line, key_name, n) && *s == ' ')			{			while (*s == ' ')				++s;			(*setup_func_cb)(s);			}		}	}static voidclient_monitor_setup(gchar *line)	{	void			(*func)();	gchar			buf[64];	gint			i;	gboolean		found_builtin = FALSE;	if (!*line || setup_done)		return;	for (i = 0; i < sizeof(monitor_table) / sizeof(KeyTable); ++i)		{		if (!strcmp(line, monitor_table[i].key))			{			func = monitor_table[i].func;			(*func)();			found_builtin = TRUE;			break;			}		}	/* The client mode init work of a plugin must be defered since they	|  aren't loaded yet.  Set up so they will can get an "available" flag.	*/	if (!found_builtin)		{		snprintf(buf, sizeof(buf), "%s available", line);		client_plugin_add_setup_line(buf);		}	}static voidclient_server_error(gchar *line)	{	fprintf(stderr, "gkrellmd error: %s\n", line);	exit(0);	}static voidlocale_sync(void)	{	struct lconv	*lc;	lc = localeconv();	locale_decimal_point = *lc->decimal_point;	if (locale_decimal_point != server_decimal_point)		need_locale_fix = TRUE;	}static voidclient_server_decimal_point(gchar *line)	{	sscanf(line, "%c", &server_decimal_point);	locale_sync();	}static voidclient_server_io_timeout(gchar *line)	{	sscanf(line, "%d", &_GK.client_server_io_timeout);	if (_GK.client_server_io_timeout < 2)		_GK.client_server_io_timeout = 0;	}static voidclient_server_reconnect_timeout(gchar *line)	{	sscanf(line, "%d", &_GK.client_server_reconnect_timeout);	if (_GK.client_server_reconnect_timeout < 2)		_GK.client_server_reconnect_timeout = 0;	}/* ================================================================= */KeyTable	setup_table[] =	{	{"<version>",		client_server_version_setup },	{"<sensors_setup>",	client_sensors_setup },	{"<hostname>",		client_hostname_setup },	{"<sysname>",		client_sysname_setup },	{"<cpu_setup>",		client_cpu_setup },	{"<disk_setup>",	client_disk_setup },	{"<inet_setup>",	client_inet_setup },	{"<net_setup>",		client_net_setup },	{"<fs_setup>",		client_fs_setup },	{"<mail_setup>",	client_mail_setup },	{"<apm_setup>",		client_battery_setup },	{"<battery_setup>",	client_battery_setup },	{"<time>",			client_time_line_from_server},	{"<monitors>",		client_monitor_setup },	{"<decimal_point>",	client_server_decimal_point },	{"<error>",			client_server_error },	{"<io_timeout>",	client_server_io_timeout},	{"<reconnect_timeout>", client_server_reconnect_timeout},	{"<plugin_setup>",	client_plugin_add_setup_line},	};typedef struct	{	GkrellmMonitor	*mon;	gchar			*key_name;	void			(*func_cb)(gchar *line);	}	ClientPlugin;static GList	*client_plugin_serve_data_list;static GkrellmFuncclient_plugin_func(gchar *line)	{	GList			*list;	ClientPlugin	*plug;	void			(*func)() = NULL;	gchar			*s;	gint			n;	for (list = client_plugin_serve_data_list; list; list = list->next)		{		plug = (ClientPlugin *) list->data;		n = strlen(plug->key_name);		s = line + n;		if (*s == '>' && !strncmp(plug->key_name, line, n))			{			func = plug->func_cb;			break;			}		}	return func;	}voidgkrellm_client_plugin_serve_data_connect(GkrellmMonitor *mon,			gchar *key_name, void (*func_cb)(gchar *line))	{	ClientPlugin	*plug;	if (!mon || !key_name || !func_cb)		return;	plug = g_new0(ClientPlugin, 1);	plug->mon = mon;	plug->key_name = g_strdup(key_name);	plug->func_cb = func_cb;	client_plugin_serve_data_list				= g_list_append(client_plugin_serve_data_list, plug);	}static gbooleanclient_send_to_server(gchar *buf)	{	gint	n;	if (!server_alive || client_fd < 0)		return FALSE;#if defined(MSG_NOSIGNAL)	n = send(client_fd, buf, strlen(buf), MSG_NOSIGNAL);#else	n = send(client_fd, buf, strlen(buf), 0);#endif	if (n < 0 && errno == EPIPE)		{		if (_GK.debug_level & DEBUG_CLIENT)			printf("Write on closed pipe to gkrellmd server.\n");		server_alive = FALSE;		return FALSE;		}	return TRUE;	}gbooleangkrellm_client_send_to_server(gchar *key_name, gchar *line)	{	gchar		*str;	gboolean	result;	if (!key_name || !line || !*line)		return FALSE;	str = g_strdup_printf("<%s>\n", key_name);	client_send_to_server(str);	g_free(str);	if (line[strlen(line) - 1] != '\n')		{		str = g_strdup_printf("%s\n", line);		result = client_send_to_server(str);		g_free(str);		}	else		result = client_send_to_server(line);	return result;	}KeyTable	update_table[] =	{	{"<cpu>",			client_cpu_line_from_server},	{"<proc>",			client_proc_line_from_server},	{"<disk>",			client_disk_line_from_server},	{"<net>",			client_net_line_from_server},	{"<net_routed>",	client_net_routed_line_from_server},	{"<net_timer>",		client_net_timer_line_from_server},	{"<mem>",			client_mem_line_from_server},	{"<swap>",			client_swap_line_from_server},	{"<fs>",			client_fs_line_from_server},	{"<fs_fstab>",		client_fstab_line_from_server},	{"<fs_mounts>",		client_mounts_line_from_server},	{"<inet>",			client_inet_line_from_server},	{"<mail>",			client_mail_line_from_server},	{"<apm>",			client_battery_line_from_server},	{"<battery>",		client_battery_line_from_server},	{"<sensors>",		client_sensors_line_from_server},	{"<time>",			client_time_line_from_server},	{"<uptime>",		client_uptime_line_from_server},//	{"<>",			client__line_from_server},	};static gintgetline(gint fd, gchar *buf, gint len)	{	fd_set			read_fds;	struct timeval	tv;	gchar			*s;	gint			result, n, nread = 0;	FD_ZERO(&read_fds);	FD_SET(fd, &read_fds);	tv.tv_usec = 0;	tv.tv_sec = 15;	s = buf;	*s = '\0';	for (n = 0; n < len - 1; ++n)		{		nread = 0;		result = select(fd + 1, &read_fds, NULL, NULL, &tv);		if (result <= 0 || (nread = recv(fd, s, 1, 0)) != 1)			break;		if (*s == '\n')			{			*s = '\0';			break;			}		*++s = '\0';		}	if (nread < 0 && errno != EINTR)		{		fprintf(stderr, "Broken server connection\n");		exit(0);		}	if (_GK.debug_level & DEBUG_CLIENT)		printf("%s\n", buf);	return n;	}static voidprocess_server_line(KeyTable *table, gint table_size, gchar *line)	{	static void		(*func)(gchar *);	gint			i;	if (!*line || *line == '#')		return;	if (*line == '<')		{		func = NULL;		if (line[1] == '.')			{			server_time.tm_sec = atoi(line + 2);			return;			}		for (i = 0; i < table_size; ++i)			{			if (!strcmp(table[i].key, line))				{				func = table[i].func;				break;				}			}		if (!func)			func = client_plugin_func(line + 1);		}	else if (func)		(*func)(line);	}  /* Read setup info from gkrellmd server.  Stuff needed before the  |  client_init calls must be read here.  */static voidread_server_setup(gint fd)	{	gchar			buf[256];	gint			table_size;	/* Pre 2.1.6 gkrellmd does not send <decimal_point>, so put a fallback	|  locale_sync() here.	*/	locale_sync();	_GK.client_server_read_time = time(0);	table_size = sizeof(setup_table) / sizeof(KeyTable);	gkrellm_free_glist_and_data(&client_plugin_setup_line_list);	while (1)		{		getline(fd, buf, sizeof(buf));		if (!strcmp(buf, "</gkrellmd_setup>"))			break;		process_server_line(&setup_table[0], table_size, buf);		}	/* Reset any data that is not cumulative.  gkrellmd sends .clear tags	|  for fstab and mounts, but inet does not.  So fix it here.	*/	client_inet_reset();	/* Read the initial update data	*/	table_size = sizeof(update_table) / sizeof(KeyTable);	while (1)		{		getline(fd, buf, sizeof(buf));		if (!strcmp(buf, "</initial_update>"))			break;		process_server_line(&update_table[0], table_size, buf);		}	setup_done = TRUE;	}voidgkrellm_client_mode_disconnect(void)	{	if (client_fd >= 0)		close(client_fd);	client_fd = -1;	server_alive = FALSE;	gdk_input_remove(client_input_id);	client_input_id = 0;	}static voidread_server_input(gpointer data, gint fd, GdkInputCondition condition)	{	gchar	*line, *eol;	gint	count, n, table_size;	n = sizeof(server_buf) - buf_index - 1;	count = recv(fd, server_buf + buf_index, n, 0);	if (count <= 0)		{		gkrellm_client_mode_disconnect();		return;		}	if (_GK.time_now > 0)		_GK.client_server_read_time = _GK.time_now;	server_buf[buf_index + count] = '\0';	line = server_buf;	table_size = sizeof(update_table) / sizeof(KeyTable);	while (*line && (eol = strchr(line, '\n')) != NULL)		{		*eol = '\0';		if (_GK.debug_level & DEBUG_CLIENT)			printf("%s\n", line);		process_server_line(&update_table[0], table_size, line);		line = eol + 1;		}	if (line != server_buf && *line)		{		buf_index = strlen(line);		memmove(server_buf, line, buf_index);		}	else if (!*line)		buf_index = 0;	else		{		buf_index += count;		if (buf_index >= sizeof(server_buf) - 2)			buf_index = 0;		}	server_buf[buf_index] = '\0';	}gintgkrellm_connect_to(gchar *server, gint server_port)	{	gint		fd	= -1;#ifdef HAVE_GETADDRINFO	gint 		rv	= 0;	struct addrinfo	hints, *res, *res0;	gchar		portnumber[6];#else	struct hostent	*addr;	struct sockaddr_in s;#endif#ifdef HAVE_GETADDRINFO	snprintf (portnumber, sizeof(portnumber), "%d", server_port);	memset(&hints, 0, sizeof(hints));	hints.ai_family = PF_UNSPEC;	hints.ai_socktype = SOCK_STREAM;	hints.ai_protocol = 0;	if ((rv = getaddrinfo(server, portnumber, &hints, &res0)) != 0)		return -1;	for (res = res0; res; res = res->ai_next)		{		if ((fd = socket(res->ai_family, res->ai_socktype,				res->ai_protocol)) < 0)			continue;		if (_GK.debug_level & DEBUG_CLIENT)			printf("\t[gkrellm_connect_to: (%d,%d,%d) %s:%d]\n",			       res->ai_family, res->ai_socktype,			       res->ai_protocol, server, server_port);		if (connect(fd, res->ai_addr, res->ai_addrlen) >= 0)			break;#ifdef WIN32		closesocket(fd);#else		close(fd);#endif		fd = -1;		}	freeaddrinfo(res0);#else	if (_GK.debug_level & DEBUG_CLIENT)		printf("\t[gkrellm_connect_to: %s:%d]\n", server, server_port);	addr = gethostbyname(server);	if (addr)		{		fd = socket(AF_INET, SOCK_STREAM, 0);		if (fd >= 0)			{			memset(&s, 0, sizeof(s));			memcpy(&s.sin_addr.s_addr, addr->h_addr, addr->h_length);			s.sin_family = AF_INET;			s.sin_port = htons(server_port);			if (connect(fd, (struct sockaddr *)&s, sizeof (s)) < 0)				{#ifdef WIN32				closesocket(fd);#else				close(fd);#endif				fd = -1;				}			}		}#endif	if (fd < 0)		return -1;	return fd;	}gbooleangkrellm_client_mode_connect(void)	{	gchar	buf[128];	if (_GK.server_port == 0)		_GK.server_port = GKRELLMD_SERVER_PORT;	client_fd = gkrellm_connect_to(_GK.server, _GK.server_port);	if (client_fd < 0) {		printf("%s\n", _("Unable to connect."));		return FALSE;	}	snprintf(buf, sizeof(buf), "gkrellm %d.%d.%d%s\n",			GKRELLM_VERSION_MAJOR, GKRELLM_VERSION_MINOR,			GKRELLM_VERSION_REV, GKRELLM_EXTRAVERSION);	send(client_fd, buf, strlen(buf), 0);	/* Initial setup lines from server are read in blocking mode.	*/	read_server_setup(client_fd);	/* Extra stuff not handled in read_server_setup()	*/	gkrellm_mail_local_unsupported();	/* Now switch to non blocking and set up a read handler.	*/	fcntl(client_fd, F_SETFL, O_NONBLOCK);	client_input_id = gdk_input_add(client_fd, GDK_INPUT_READ,					(GdkInputFunction) read_server_input, NULL);	server_alive = TRUE;	return TRUE;	}static gboolean	client_mode_thread_busy;gintgkrellm_client_server_connect_state(void)	{	if (client_mode_thread_busy)			/* reconnect in progress? */		return 2;	if (_GK.client_mode && client_input_id > 0)	/* Currently connected? */		return 1;	else if (_GK.client_mode)		return 0;	else		return -1;	}static gpointerclient_mode_connect_thread(void *data)	{	gkrellm_client_mode_connect();	client_mode_thread_busy = FALSE;	return NULL;	}voidgkrellm_client_mode_connect_thread(void)	{	if (client_mode_thread_busy || !_GK.client_mode)		return;	client_mode_thread_busy = TRUE;	g_thread_create(client_mode_connect_thread, NULL, FALSE, NULL);	}gbooleangkrellm_client_mode(void)	{	return _GK.client_mode;	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -