[asterisk-commits] russell: branch russell/events2 r145321 - in /team/russell/events2: configs/ ...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Tue Sep 30 23:39:04 CDT 2008


Author: russell
Date: Tue Sep 30 23:39:03 2008
New Revision: 145321

URL: http://svn.digium.com/view/asterisk?view=rev&rev=145321
Log:
Back up a work in progress - res_eventpeer.  This module will eventually provide
peer to peer event sharing over TCP/TLS.

Added:
    team/russell/events2/configs/res_eventpeer.conf.sample   (with props)
    team/russell/events2/res/res_eventpeer.c   (with props)
Modified:
    team/russell/events2/include/asterisk/event.h
    team/russell/events2/include/asterisk/event_defs.h
    team/russell/events2/main/event.c

Added: team/russell/events2/configs/res_eventpeer.conf.sample
URL: http://svn.digium.com/view/asterisk/team/russell/events2/configs/res_eventpeer.conf.sample?view=auto&rev=145321
==============================================================================
--- team/russell/events2/configs/res_eventpeer.conf.sample (added)
+++ team/russell/events2/configs/res_eventpeer.conf.sample Tue Sep 30 23:39:03 2008
@@ -1,0 +1,31 @@
+[general]
+;enabled = yes
+;bindaddr = 0.0.0.0:7103
+;tlsenabled = yes
+;tlsbindaddr = 0.0.0.0:7104
+;tlscert = asterisk.pem
+
+;tlscafile=</path/to/certificate>
+;        If the server your connecting to uses a self signed certificate
+;        you should have their certificate installed here so the code can 
+;        verify the authenticity of their certificate.
+
+;tlscapath=</path/to/ca/dir>
+;        A directory full of CA certificates.  The files must be named with 
+;        the CA subject name hash value. 
+;        (see man SSL_CTX_load_verify_locations for more info) 
+
+;tlsverifyclient=[yes|no]
+;        Stuff and things.
+
+;tlsdontverifyserver=[yes|no]
+;        If set to yes, don't verify the servers certificate when acting as 
+;        a client.  If you don't have the server's CA certificate you can
+;        set this and it will connect without requiring tlscafile to be set.
+;        Default is no.
+
+;tlscipher=<SSL cipher string>
+;        A string specifying which SSL ciphers to use or not use
+;        A list of valid SSL cipher strings can be found at: 
+;                http://www.openssl.org/docs/apps/ciphers.html#CIPHER_STRINGS
+

Propchange: team/russell/events2/configs/res_eventpeer.conf.sample
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: team/russell/events2/configs/res_eventpeer.conf.sample
------------------------------------------------------------------------------
    svn:keywords = Author Date Id Revision

Propchange: team/russell/events2/configs/res_eventpeer.conf.sample
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Modified: team/russell/events2/include/asterisk/event.h
URL: http://svn.digium.com/view/asterisk/team/russell/events2/include/asterisk/event.h?view=diff&rev=145321&r1=145320&r2=145321
==============================================================================
--- team/russell/events2/include/asterisk/event.h (original)
+++ team/russell/events2/include/asterisk/event.h Tue Sep 30 23:39:03 2008
@@ -578,6 +578,8 @@
  */
 size_t ast_event_get_size(const struct ast_event *event);
 
+struct ast_event *ast_event_dup(const struct ast_event *event);
+
 /*!
  * \brief Initialize an event iterator instance
  *

Modified: team/russell/events2/include/asterisk/event_defs.h
URL: http://svn.digium.com/view/asterisk/team/russell/events2/include/asterisk/event_defs.h?view=diff&rev=145321&r1=145320&r2=145321
==============================================================================
--- team/russell/events2/include/asterisk/event_defs.h (original)
+++ team/russell/events2/include/asterisk/event_defs.h Tue Sep 30 23:39:03 2008
@@ -151,10 +151,28 @@
 	AST_EVENT_SUB_EXISTS,
 };
 
-struct ast_event;
 struct ast_event_ie;
 struct ast_event_sub;
 struct ast_event_iterator;
+
+/*!
+ * \brief An event
+ *
+ * An ast_event consists of an event header (this structure), and zero or
+ * more information elements defined by ast_event_ie.
+ *
+ * \note The format of this structure is important.  Since these events may
+ *       be sent directly over a network, changing this structure will break
+ *       compatibility with older versions.
+ */
+struct ast_event {
+	/*! Event type */
+	enum ast_event_type type:16;
+	/*! Total length of the event */
+	uint16_t event_len:16;
+	/*! The data payload of the event, made up of information elements */
+	unsigned char payload[0];
+} __attribute__ ((packed));
 
 /*!
  * \brief supposed to be an opaque type

Modified: team/russell/events2/main/event.c
URL: http://svn.digium.com/view/asterisk/team/russell/events2/main/event.c?view=diff&rev=145321&r1=145320&r2=145321
==============================================================================
--- team/russell/events2/main/event.c (original)
+++ team/russell/events2/main/event.c Tue Sep 30 23:39:03 2008
@@ -52,26 +52,6 @@
 	/*! Total length of the IE payload */
 	uint16_t ie_payload_len;
 	unsigned char ie_payload[0];
-} __attribute__ ((packed));
-
-/*!
- * \brief An event
- *
- * An ast_event consists of an event header (this structure), and zero or
- * more information elements defined by ast_event_ie.
- *
- * \note The format of this structure is important.  Since these events may
- *       be sent directly over a network, changing this structure will break
- *       compatibility with older versions.  However, at this point, this code
- *       has not made it into a release, so it is still fair game for change.
- */
-struct ast_event {
-	/*! Event type */
-	enum ast_event_type type:16;
-	/*! Total length of the event */
-	uint16_t event_len:16;
-	/*! The data payload of the event, made up of information elements */
-	unsigned char payload[0];
 } __attribute__ ((packed));
 
 struct ast_event_ref {
@@ -856,7 +836,7 @@
 	ast_free(event_ref);
 }
 
-static struct ast_event *ast_event_dup(const struct ast_event *event)
+struct ast_event *ast_event_dup(const struct ast_event *event)
 {
 	struct ast_event *dup_event;
 	uint16_t event_len;

Added: team/russell/events2/res/res_eventpeer.c
URL: http://svn.digium.com/view/asterisk/team/russell/events2/res/res_eventpeer.c?view=auto&rev=145321
==============================================================================
--- team/russell/events2/res/res_eventpeer.c (added)
+++ team/russell/events2/res/res_eventpeer.c Tue Sep 30 23:39:03 2008
@@ -1,0 +1,369 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2008, Digium, Inc.
+ *
+ * Russell Bryant <russell at digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief High Performance Event Peering
+ *
+ * \author Russell Bryant <russell at digium.com>
+ */
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/event.h"
+#include "asterisk/tcptls.h"
+#include "asterisk/config.h"
+#include "asterisk/utils.h"
+#include "asterisk/lock.h"
+#include "asterisk/cli.h"
+
+static const char cfg_file[] = "res_eventpeer.conf";
+
+static const uint16_t default_port     = 7103;
+static const uint16_t default_tls_port = 7104;
+
+static struct {
+	unsigned int enabled:1;
+	unsigned int tls_enabled:1;
+	ast_mutex_t reload_lock;
+	struct ast_tls_config tls;
+} g_config;
+
+static void *eventpeer_tcp_worker_fn(void *data);
+
+static struct server_args eventpeer_tcp_desc = {
+	.accept_fd = -1,
+	.master = AST_PTHREADT_NULL,
+	.tls_cfg = NULL,
+	.poll_timeout = -1,
+	.name = "eventpeer TCP server",
+	.accept_fn = ast_tcptls_server_root,
+	.worker_fn = eventpeer_tcp_worker_fn,
+};
+
+static struct server_args eventpeer_tls_desc = {
+	.accept_fd = -1,
+	.master = AST_PTHREADT_NULL,
+	.tls_cfg = &g_config.tls,
+	.poll_timeout = -1,
+	.name = "eventpeer TLS server",
+	.accept_fn = ast_tcptls_server_root,
+	.worker_fn = eventpeer_tcp_worker_fn,
+};
+
+static void *eventpeer_tcp_worker_fn(void *data)
+{
+	struct ast_tcptls_session_instance *session = data;
+	int res;
+	struct ast_event *event;
+	char buf[4096];
+
+	for (;;) {
+		size_t event_len;
+
+		res = ast_wait_for_input(session->fd, -1);
+		if (res < 0) {
+			ast_debug(1, "wait_for_input returned %d\n", res);
+			break;
+		}
+
+		event = (struct ast_event *) buf;
+
+		res = fread(buf, 1, sizeof(*event), session->f);
+		if (res < 0) {
+			ast_log(LOG_ERROR, "fread() returned error: %s\n", strerror(errno));
+			break;
+		}
+		
+		/* Now we have an event header, so read in the rest of the event */
+
+		event_len = ast_event_get_size(event);
+		if (event_len > sizeof(buf)) {
+			ast_log(LOG_ERROR, "Buffer not big enough for an event of %lu bytes\n", 
+					event_len);
+			break;
+		}
+
+		res = fread(buf + sizeof(*event), 1, event_len - sizeof(*event), session->f);
+		if (res < 0) {
+			ast_log(LOG_ERROR, "fread() returned error: %s\n", strerror(errno));
+			break;
+		}
+
+		if (!(event = ast_event_dup(event))) {
+			ast_log(LOG_WARNING, "Failed to duplicate event :(\n");
+			continue;
+		}
+
+		ast_event_queue(event);
+		event = NULL;
+	}
+
+	fclose(session->f);
+	session->f = NULL;
+	session->fd = -1;
+	ao2_ref(session, -1);
+	session = NULL;
+
+	return NULL;
+}
+
+static void store_bindaddr(const char *val, struct sockaddr_in *sin)
+{
+	if (ast_parse_arg(val, PARSE_INADDR | PARSE_PORT_MASK, sin)) {
+		ast_log(LOG_WARNING, "Invalid bindaddr format '%s'\n", val);
+	}
+}
+
+static void store_general_config(const char *name, const char *val)
+{
+	CV_START(name, val);
+	
+	CV_BOOL("enabled", g_config.enabled);
+	CV_BOOL("enable", g_config.enabled);
+	CV_F("bindaddr", store_bindaddr(val, &eventpeer_tcp_desc.sin));
+
+	CV_BOOL("tlsenabled", g_config.tls_enabled);
+	CV_BOOL("tlsenable", g_config.tls_enabled);
+	CV_F("tlsbindaddr", store_bindaddr(val, &eventpeer_tls_desc.sin));
+	CV_DSTR("tlscertfile", g_config.tls.certfile);
+	CV_DSTR("tlscipher", g_config.tls.cipher);
+	CV_DSTR("tlscafile", g_config.tls.cafile);
+	CV_DSTR("tlscadir", g_config.tls.capath);
+	CV_DSTR("tlscapath", g_config.tls.capath);
+	CV_F("tlsdontverifyserver", 
+		ast_set2_flag(&g_config.tls.flags, ast_true(val), AST_SSL_DONT_VERIFY_SERVER));
+	CV_F("tlsverifyclient", 
+		ast_set2_flag(&g_config.tls.flags, ast_true(val), AST_SSL_VERIFY_CLIENT));
+
+	ast_log(LOG_WARNING, "Unknown option '%s' in the general section of %s\n",
+			name, cfg_file);
+
+	CV_END;
+}
+
+static void reset_general_settings(int destroy_only)
+{
+	g_config.enabled = 0;
+	memset(&eventpeer_tcp_desc.sin, 0, sizeof(eventpeer_tcp_desc.sin));
+	eventpeer_tcp_desc.sin.sin_family = AF_INET;
+	eventpeer_tcp_desc.sin.sin_port = htons(default_port);
+
+	g_config.tls_enabled = 0;
+	memset(&eventpeer_tls_desc.sin, 0, sizeof(eventpeer_tls_desc.sin));
+	eventpeer_tls_desc.sin.sin_family = AF_INET;
+	eventpeer_tls_desc.sin.sin_port = htons(default_tls_port);
+
+	g_config.tls.flags.flags = 0;
+	if (g_config.tls.certfile) {
+		ast_free(g_config.tls.certfile);
+		g_config.tls.certfile = NULL;
+	}
+	if (!destroy_only) {
+		g_config.tls.certfile = ast_strdup(AST_CERTFILE);
+	}
+	if (g_config.tls.cipher) {
+		ast_free(g_config.tls.cipher);
+		g_config.tls.cipher = NULL;
+	}
+	if (!destroy_only) {
+		g_config.tls.cipher = ast_strdup("");
+	}
+	if (g_config.tls.cafile) {
+		ast_free(g_config.tls.cafile);
+		g_config.tls.cafile = NULL;
+	}
+	if (!destroy_only) {
+		g_config.tls.cafile = ast_strdup("");
+	}
+	if (g_config.tls.capath) {
+		ast_free(g_config.tls.capath);
+		g_config.tls.capath = NULL;
+	}
+	if (!destroy_only) {
+		g_config.tls.capath = ast_strdup("");
+	}
+}
+
+static void load_event_peer(struct ast_config *cfg, const char *cat)
+{
+	/* XXX */
+}
+
+static void post_config_init(void)
+{
+	if (!g_config.enabled) {
+		eventpeer_tcp_desc.sin.sin_family = 0;
+	}
+	ast_tcptls_server_start(&eventpeer_tcp_desc);
+
+	if (!g_config.tls_enabled) {
+		eventpeer_tls_desc.sin.sin_family = 0;
+	}
+	if (ast_ssl_setup(eventpeer_tls_desc.tls_cfg)) {
+		ast_tcptls_server_start(&eventpeer_tls_desc);
+	}
+}
+
+static int load_config(int reload)
+{
+	struct ast_config *cfg;
+	struct ast_flags cfg_flags = { CONFIG_FLAG_FILEUNCHANGED };
+	const char *cat = NULL;
+	struct ast_variable *var;
+
+	cfg = ast_config_load(cfg_file, cfg_flags);
+	if (cfg == CONFIG_STATUS_FILEUNCHANGED && reload) {
+		return 0;
+	} else if (!cfg) {
+		ast_log(LOG_ERROR, "error loading config file - %s\n", cfg_file);
+		return -1;
+	}
+
+	ast_mutex_lock(&g_config.reload_lock);
+
+	reset_general_settings(0);
+
+	for (var = ast_variable_browse(cfg, "general"); var; var = var->next) {
+		store_general_config(var->name, var->value);
+	}
+
+	while ((cat = ast_category_browse(cfg, cat))) {
+		if (strcasecmp(cat, "general")) {
+			load_event_peer(cfg, cat);
+		}
+	}
+
+	ast_config_destroy(cfg);
+
+	post_config_init();
+
+	ast_mutex_unlock(&g_config.reload_lock);
+
+	return 0;
+}
+
+static char *cli_show_settings(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
+{
+	switch (cmd) {
+	case CLI_INIT:
+		e->command = "eventpeer show settings";
+		e->usage =
+			"Usage: eventpeer show settings\n"
+			"   This command shows the current general settings for res_eventpeer\n"
+			"";
+		return NULL;
+	case CLI_GENERATE:
+		return NULL;
+	}
+
+	if (a->argc != e->args) {
+		return CLI_SHOWUSAGE;
+	}
+
+	ast_cli(a->fd, "\n"
+	            "=============================================================\n"
+	            "=== res_eventpeer General Settings ==========================\n"
+	            "=============================================================\n"
+	            "");
+
+	ast_mutex_lock(&g_config.reload_lock);
+
+	ast_cli(a->fd, "===\n"
+	               "=== TCP Server Settings:\n"
+				   "=== ==> Enabled:   %s\n"
+	               "=== ==> Bind Addr: %s:%d\n", 
+			g_config.enabled ? "Yes" : "No",	
+			ast_inet_ntoa(eventpeer_tcp_desc.sin.sin_addr),
+			htons(eventpeer_tcp_desc.sin.sin_port));
+	        
+	ast_cli(a->fd, "===\n"
+	               "=== TLS Server Settings:\n"
+	               "=== ==> Enabled:            %s\n"
+	               "=== ==> Bind Addr:          %s:%d\n"
+	               "=== ==> Certificate:        %s\n"
+	               "=== ==> Cipher:             %s\n"
+	               "=== ==> CA File:            %s\n"
+	               "=== ==> CA Path:            %s\n"
+				   "=== ==> Verify Client Cert: %s\n"
+	               "",
+			g_config.tls.enabled ? "Yes" : "No",
+			ast_inet_ntoa(eventpeer_tls_desc.sin.sin_addr),
+			htons(eventpeer_tls_desc.sin.sin_port),
+			g_config.tls.certfile, g_config.tls.cipher, g_config.tls.cafile,
+			g_config.tls.capath,
+			ast_test_flag(&g_config.tls.flags, AST_SSL_VERIFY_CLIENT) ? "Yes" : "No");
+
+	ast_cli(a->fd, "===\n"
+	               "=== TLS Client Settings:\n"
+	               "=== ==> Verify Server Cert: %s\n"
+	               "",
+			ast_test_flag(&g_config.tls.flags, AST_SSL_DONT_VERIFY_SERVER) ? "No" : "Yes");
+				
+	ast_mutex_unlock(&g_config.reload_lock);
+
+	ast_cli(a->fd, "===\n"
+	               "=============================================================\n\n");
+
+	return CLI_SUCCESS;
+}
+
+static int module_reload(void)
+{
+	return load_config(1);
+}
+
+static struct ast_cli_entry cli_eventpeer[] = {
+	AST_CLI_DEFINE(cli_show_settings, "Show General Settings"),
+};
+
+static int module_unload(void)
+{
+	ast_cli_unregister_multiple(cli_eventpeer, ARRAY_LEN(cli_eventpeer));
+
+	ast_tcptls_server_stop(&eventpeer_tcp_desc);
+	ast_tcptls_server_stop(&eventpeer_tls_desc);
+
+	ast_mutex_destroy(&g_config.reload_lock);
+
+	reset_general_settings(1);
+
+	return 0;
+}
+
+static int module_load(void)
+{
+	ast_mutex_init(&g_config.reload_lock);
+
+	if (load_config(0)) {
+		return AST_MODULE_LOAD_DECLINE;
+	}
+
+	ast_cli_register_multiple(cli_eventpeer, ARRAY_LEN(cli_eventpeer));
+	
+	return AST_MODULE_LOAD_SUCCESS;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_DEFAULT, "High Performance Event Peering",
+	.load   = module_load,
+	.unload = module_unload,
+	.reload = module_reload,
+);

Propchange: team/russell/events2/res/res_eventpeer.c
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: team/russell/events2/res/res_eventpeer.c
------------------------------------------------------------------------------
    svn:keywords = Author Date Id Revision

Propchange: team/russell/events2/res/res_eventpeer.c
------------------------------------------------------------------------------
    svn:mime-type = text/plain




More information about the asterisk-commits mailing list