From 680345d374740c176352bc289e6aa29ed1595455 Mon Sep 17 00:00:00 2001 From: Johan Wikman Date: Thu, 12 Nov 2015 14:58:11 +0200 Subject: [PATCH] Whitespace cleanup of config.c - Tabs replaced with spaces. - Allman indentation style --- server/core/config.c | 4235 ++++++++++++++++++++++-------------------- 1 file changed, 2178 insertions(+), 2057 deletions(-) diff --git a/server/core/config.c b/server/core/config.c index a1497adc8..8927def5d 100644 --- a/server/core/config.c +++ b/server/core/config.c @@ -22,27 +22,27 @@ * @verbatim * Revision History * - * Date Who Description - * 21/06/13 Mark Riddoch Initial implementation - * 08/07/13 Mark Riddoch Addition on monitor module support - * 23/07/13 Mark Riddoch Addition on default monitor password - * 06/02/14 Massimiliano Pinto Added support for enable/disable root user in services - * 14/02/14 Massimiliano Pinto Added enable_root_user in the service_params list - * 11/03/14 Massimiliano Pinto Added Unix socket support - * 11/05/14 Massimiliano Pinto Added version_string support to service - * 19/05/14 Mark Riddoch Added unique names from section headers - * 29/05/14 Mark Riddoch Addition of filter definition - * 23/05/14 Massimiliano Pinto Added automatic set of maxscale-id: first listening ipv4_raw + port + pid - * 28/05/14 Massimiliano Pinto Added detect_replication_lag parameter - * 28/08/14 Massimiliano Pinto Added detect_stale_master parameter - * 09/09/14 Massimiliano Pinto Added localhost_match_wildcard_host parameter - * 12/09/14 Mark Riddoch Addition of checks on servers list and - * internal router suppression of messages - * 30/10/14 Massimiliano Pinto Added disable_master_failback parameter - * 07/11/14 Massimiliano Pinto Addition of monitor timeouts for connect/read/write - * 20/02/15 Markus Mäkelä Added connection_timeout parameter for services - * 05/03/15 Massimiliano Pinto Added notification_feedback support - * 20/04/15 Guillaume Lefranc Added available_when_donor parameter + * Date Who Description + * 21/06/13 Mark Riddoch Initial implementation + * 08/07/13 Mark Riddoch Addition on monitor module support + * 23/07/13 Mark Riddoch Addition on default monitor password + * 06/02/14 Massimiliano Pinto Added support for enable/disable root user in services + * 14/02/14 Massimiliano Pinto Added enable_root_user in the service_params list + * 11/03/14 Massimiliano Pinto Added Unix socket support + * 11/05/14 Massimiliano Pinto Added version_string support to service + * 19/05/14 Mark Riddoch Added unique names from section headers + * 29/05/14 Mark Riddoch Addition of filter definition + * 23/05/14 Massimiliano Pinto Added automatic set of maxscale-id: first listening ipv4_raw + port + pid + * 28/05/14 Massimiliano Pinto Added detect_replication_lag parameter + * 28/08/14 Massimiliano Pinto Added detect_stale_master parameter + * 09/09/14 Massimiliano Pinto Added localhost_match_wildcard_host parameter + * 12/09/14 Mark Riddoch Addition of checks on servers list and + * internal router suppression of messages + * 30/10/14 Massimiliano Pinto Added disable_master_failback parameter + * 07/11/14 Massimiliano Pinto Addition of monitor timeouts for connect/read/write + * 20/02/15 Markus Mäkelä Added connection_timeout parameter for services + * 05/03/15 Massimiliano Pinto Added notification_feedback support + * 20/04/15 Guillaume Lefranc Added available_when_donor parameter * 22/04/15 Martin Brampton Added disable_master_role_setting parameter * * @endverbatim @@ -83,50 +83,54 @@ #define MAXSCALE_PCRE_BUFSZ 24 extern int setipaddress(struct in_addr *, char *); -static int process_config_context(CONFIG_CONTEXT *); -static int process_config_update(CONFIG_CONTEXT *); -static void free_config_context(CONFIG_CONTEXT *); -static char *config_get_value(CONFIG_PARAMETER *, const char *); -static const char *config_get_value_string(CONFIG_PARAMETER *, const char *); -static int handle_global_item(const char *, const char *); -static int handle_feedback_item(const char *, const char *); -static void global_defaults(); -static void feedback_defaults(); -static void check_config_objects(CONFIG_CONTEXT *context); +static int process_config_context(CONFIG_CONTEXT *); +static int process_config_update(CONFIG_CONTEXT *); +static void free_config_context(CONFIG_CONTEXT *); +static char *config_get_value(CONFIG_PARAMETER *, const char *); +static const char *config_get_value_string(CONFIG_PARAMETER *, const char *); +static int handle_global_item(const char *, const char *); +static int handle_feedback_item(const char *, const char *); +static void global_defaults(); +static void feedback_defaults(); +static void check_config_objects(CONFIG_CONTEXT *context); static int maxscale_getline(char** dest, int* size, FILE* file); -int config_truth_value(char *str); -bool isInternalService(char *router); -int config_get_ifaddr(unsigned char *output); -int config_get_release_string(char* release); -FEEDBACK_CONF * config_get_feedback_data(); -void config_add_param(CONFIG_CONTEXT*,char*,char*); +int config_truth_value(char *str); +bool isInternalService(char *router); +int config_get_ifaddr(unsigned char *output); +int config_get_release_string(char* release); +FEEDBACK_CONF *config_get_feedback_data(); +void config_add_param(CONFIG_CONTEXT*, char*, char*); bool config_has_duplicate_sections(const char* config); -static char *config_file = NULL; -static GATEWAY_CONF gateway; -static FEEDBACK_CONF feedback; -char *version_string = NULL; +static char *config_file = NULL; +static GATEWAY_CONF gateway; +static FEEDBACK_CONF feedback; +char *version_string = NULL; /** * Trim whitespace from the front and rear of a string * - * @param str String to trim - * @return Trimmed string, changes are done in situ + * @param str String to trim + * @return Trimmed string, changes are done in situ */ static char * trim(char *str) { -char *ptr; + char *ptr; - while (isspace(*str)) - str++; + while (isspace(*str)) + { + str++; + } - /* Point to last character of the string */ - ptr = str + strlen(str) - 1; - while (ptr > str && isspace(*ptr)) - *ptr-- = 0; + /* Point to last character of the string */ + ptr = str + strlen(str) - 1; + while (ptr > str && isspace(*ptr)) + { + *ptr-- = 0; + } - return str; + return str; } /** @@ -139,35 +143,36 @@ char* config_clean_string_list(char* str) { char *tmp; - if((tmp = malloc(sizeof(char)*(strlen(str) + 1))) != NULL) + if ((tmp = malloc(sizeof(char) * (strlen(str) + 1))) != NULL) { char *ptr; int match[MAXSCALE_PCRE_BUFSZ]; pcre* re; const char *re_err; - int err_offset,rval; - + int err_offset, rval; tmp[0] = '\0'; - if((re = pcre_compile("\\s*+([^,]*[^,\\s])",0,&re_err,&err_offset,NULL)) == NULL) + if ((re = pcre_compile("\\s*+([^,]*[^,\\s])", 0, &re_err, &err_offset, NULL)) == NULL) { - skygw_log_write(LE,"[%s] Error: Regular expression compilation failed at %d: %s", - __FUNCTION__,err_offset,re_err); + skygw_log_write(LE, "[%s] Error: Regular expression compilation failed at %d: %s", + __FUNCTION__, err_offset, re_err); free(tmp); return NULL; } ptr = str; - while((rval = pcre_exec(re,NULL,ptr,strlen(ptr),0,0,(int*)&match,MAXSCALE_PCRE_BUFSZ)) > 1) + while ((rval = pcre_exec(re, NULL, ptr, strlen(ptr), 0, 0, (int*)&match, MAXSCALE_PCRE_BUFSZ)) > 1) { const char* substr; - pcre_get_substring(ptr,(int*)&match,rval,1,&substr); - if(strlen(tmp) > 0) - strcat(tmp,","); - strcat(tmp,substr); + pcre_get_substring(ptr, (int*)&match, rval, 1, &substr); + if (strlen(tmp) > 0) + { + strcat(tmp, ","); + } + strcat(tmp, substr); pcre_free_substring(substr); ptr = &ptr[match[1]]; } @@ -175,7 +180,7 @@ char* config_clean_string_list(char* str) } else { - skygw_log_write(LE,"[%s] Error: Memory allocation failed.",__FUNCTION__); + skygw_log_write(LE, "[%s] Error: Memory allocation failed.", __FUNCTION__); } return tmp; @@ -183,173 +188,192 @@ char* config_clean_string_list(char* str) /** * Config item handler for the ini file reader * - * @param userdata The config context element - * @param section The config file section - * @param name The Parameter name - * @param value The Parameter value + * @param userdata The config context element + * @param section The config file section + * @param name The Parameter name + * @param value The Parameter value * @return zero on error */ static int handler(void *userdata, const char *section, const char *name, const char *value) { -CONFIG_CONTEXT *cntxt = (CONFIG_CONTEXT *)userdata; -CONFIG_CONTEXT *ptr = cntxt; -CONFIG_PARAMETER *param, *p1; + CONFIG_CONTEXT *cntxt = (CONFIG_CONTEXT *)userdata; + CONFIG_CONTEXT *ptr = cntxt; + CONFIG_PARAMETER *param, *p1; - if (strcmp(section, "gateway") == 0 || strcasecmp(section, "MaxScale") == 0) - { - return handle_global_item(name, value); - } + if (strcmp(section, "gateway") == 0 || strcasecmp(section, "MaxScale") == 0) + { + return handle_global_item(name, value); + } - if (strcasecmp(section, "feedback") == 0) - { - return handle_feedback_item(name, value); - } + if (strcasecmp(section, "feedback") == 0) + { + return handle_feedback_item(name, value); + } - /* - * If we already have some parameters for the object - * add the parameters to that object. If not create - * a new object. - */ - while (ptr && strcmp(ptr->object, section) != 0) - ptr = ptr->next; - if (!ptr) - { - if ((ptr = (CONFIG_CONTEXT *)malloc(sizeof(CONFIG_CONTEXT))) == NULL) - return 0; - ptr->object = strdup(section); - ptr->parameters = NULL; - ptr->next = cntxt->next; - ptr->element = NULL; - cntxt->next = ptr; - } - /* Check to see if the parameter already exists for the section */ - p1 = ptr->parameters; - while (p1) - { - if (!strcmp(p1->name, name)) - { - char *tmp; - int paramlen = strlen(p1->value) + strlen(value) + 2; + /* + * If we already have some parameters for the object + * add the parameters to that object. If not create + * a new object. + */ + while (ptr && strcmp(ptr->object, section) != 0) + { + ptr = ptr->next; + } - if((tmp = realloc(p1->value,sizeof(char) * (paramlen))) == NULL) - { - skygw_log_write(LE,"[%s] Error: Memory allocation failed.",__FUNCTION__); - return 0; - } - strcat(tmp,","); - strcat(tmp,value); - if((p1->value = config_clean_string_list(tmp)) == NULL) - { - p1->value = tmp; - skygw_log_write(LE,"[%s] Error: Cleaning configuration parameter failed.",__FUNCTION__); - return 0; - } - free(tmp); - return 1; - } - p1 = p1->next; - } + if (!ptr) + { + if ((ptr = (CONFIG_CONTEXT *)malloc(sizeof(CONFIG_CONTEXT))) == NULL) + { + return 0; + } + ptr->object = strdup(section); + ptr->parameters = NULL; + ptr->next = cntxt->next; + ptr->element = NULL; + cntxt->next = ptr; + } + /* Check to see if the parameter already exists for the section */ + p1 = ptr->parameters; + while (p1) + { + if (!strcmp(p1->name, name)) + { + char *tmp; + int paramlen = strlen(p1->value) + strlen(value) + 2; - if ((param = (CONFIG_PARAMETER *)malloc(sizeof(CONFIG_PARAMETER))) == NULL) - return 0; - param->name = strdup(name); - param->value = strdup(value); - param->next = ptr->parameters; - ptr->parameters = param; + if ((tmp = realloc(p1->value, sizeof(char) * (paramlen))) == NULL) + { + skygw_log_write(LE, "[%s] Error: Memory allocation failed.", __FUNCTION__); + return 0; + } + strcat(tmp, ","); + strcat(tmp, value); + if ((p1->value = config_clean_string_list(tmp)) == NULL) + { + p1->value = tmp; + skygw_log_write(LE, "[%s] Error: Cleaning configuration parameter failed.", __FUNCTION__); + return 0; + } + free(tmp); + return 1; + } + p1 = p1->next; + } - return 1; + if ((param = (CONFIG_PARAMETER *)malloc(sizeof(CONFIG_PARAMETER))) == NULL) + { + return 0; + } + + param->name = strdup(name); + param->value = strdup(value); + param->next = ptr->parameters; + ptr->parameters = param; + + return 1; } /** * Load the configuration file for the MaxScale * - * @param file The filename of the configuration file + * @param file The filename of the configuration file * @return A zero return indicates a fatal error reading the configuration */ int config_load(char *file) { -CONFIG_CONTEXT config; -int rval, ini_rval; + CONFIG_CONTEXT config; + int rval, ini_rval; if (config_has_duplicate_sections(file)) { return 0; } - MYSQL *conn; - conn = mysql_init(NULL); - if (conn) { - if (mysql_real_connect(conn, NULL, NULL, NULL, NULL, 0, NULL, 0)) { - char *ptr,*tmp; - - tmp = (char *)mysql_get_server_info(conn); - unsigned int server_version = mysql_get_server_version(conn); - - if(version_string) - free(version_string); - - if((version_string = malloc(strlen(tmp) + strlen("5.5.5-") + 1)) == NULL) - return 0; - - if (server_version >= 100000) - { - strcpy(version_string,"5.5.5-"); - strcat(version_string,tmp); - } - else - { - strcpy(version_string,tmp); - } - - ptr = strstr(version_string, "-embedded"); - if (ptr) { - *ptr = '\0'; - } - - - } - mysql_close(conn); - } - - global_defaults(); - feedback_defaults(); - - config.object = ""; - config.next = NULL; - - if (( ini_rval = ini_parse(file, handler, &config)) != 0) + MYSQL *conn; + conn = mysql_init(NULL); + if (conn) + { + if (mysql_real_connect(conn, NULL, NULL, NULL, NULL, 0, NULL, 0)) { - char errorbuffer[1024 + 1]; + char *ptr, *tmp; - if (ini_rval > 0) - snprintf(errorbuffer, sizeof(errorbuffer), - "Error: Failed to parse configuration file. Error on line %d.", ini_rval); - else if(ini_rval == -1) - snprintf(errorbuffer, sizeof(errorbuffer), - "Error: Failed to parse configuration file. Failed to open file."); + tmp = (char *)mysql_get_server_info(conn); + unsigned int server_version = mysql_get_server_version(conn); + + if (version_string) + { + free(version_string); + } + + if ((version_string = malloc(strlen(tmp) + strlen("5.5.5-") + 1)) == NULL) + { + return 0; + } + + if (server_version >= 100000) + { + strcpy(version_string, "5.5.5-"); + strcat(version_string, tmp); + } else - snprintf(errorbuffer, sizeof(errorbuffer), - "Error: Failed to parse configuration file. Memory allocation failed."); + { + strcpy(version_string, tmp); + } - skygw_log_write(LE, errorbuffer); - return 0; + ptr = strstr(version_string, "-embedded"); + if (ptr) + { + *ptr = '\0'; + } + } + mysql_close(conn); + } + + global_defaults(); + feedback_defaults(); + + config.object = ""; + config.next = NULL; + + if ((ini_rval = ini_parse(file, handler, &config)) != 0) + { + char errorbuffer[1024 + 1]; + + if (ini_rval > 0) + { + snprintf(errorbuffer, sizeof(errorbuffer), + "Error: Failed to parse configuration file. Error on line %d.", ini_rval); + } + else if(ini_rval == -1) + { + snprintf(errorbuffer, sizeof(errorbuffer), + "Error: Failed to parse configuration file. Failed to open file."); + } + else + { + snprintf(errorbuffer, sizeof(errorbuffer), + "Error: Failed to parse configuration file. Memory allocation failed."); } - config_file = file; + skygw_log_write(LE, errorbuffer); + return 0; + } - check_config_objects(config.next); - rval = process_config_context(config.next); - free_config_context(config.next); + config_file = file; + + check_config_objects(config.next); + rval = process_config_context(config.next); + free_config_context(config.next); /** Start all monitors */ - if(rval) + if (rval) { monitorStartAll(); } - return rval; + return rval; } /** @@ -360,147 +384,129 @@ int rval, ini_rval; int config_reload() { -CONFIG_CONTEXT config; -int rval; + CONFIG_CONTEXT config; + int rval; - if (!config_file) - return 0; + if (!config_file) + { + return 0; + } if (config_has_duplicate_sections(config_file)) { return 0; } - if (gateway.version_string) - free(gateway.version_string); + if (gateway.version_string) + { + free(gateway.version_string); + } - global_defaults(); + global_defaults(); - config.object = ""; - config.next = NULL; + config.object = ""; + config.next = NULL; - if (ini_parse(config_file, handler, &config) < 0) - return 0; + if (ini_parse(config_file, handler, &config) < 0) + { + return 0; + } - rval = process_config_update(config.next); - free_config_context(config.next); + rval = process_config_update(config.next); + free_config_context(config.next); - return rval; + return rval; } /** * Process a configuration context and turn it into the set of object * we need. * - * @param context The configuration data + * @param context The configuration data * @return A zero result indicates a fatal error */ -static int +static int process_config_context(CONFIG_CONTEXT *context) { CONFIG_CONTEXT *obj; int error_count = 0; HASHTABLE* monitorhash; - if((monitorhash = hashtable_alloc(5,simple_str_hash,strcmp)) == NULL) + if ((monitorhash = hashtable_alloc(5, simple_str_hash, strcmp)) == NULL) { - skygw_log_write(LOGFILE_ERROR,"Error: Failed to allocate ,monitor configuration check hashtable."); + skygw_log_write(LOGFILE_ERROR, "Error: Failed to allocate, monitor configuration check hashtable."); return 0; } - hashtable_memory_fns(monitorhash,(HASHMEMORYFN)strdup,NULL,(HASHMEMORYFN)free,NULL); + hashtable_memory_fns(monitorhash, (HASHMEMORYFN)strdup, NULL, (HASHMEMORYFN)free, NULL); /** - * Process the data and create the services and servers defined - * in the data. - */ - obj = context; - while (obj) - { - char *type = config_get_value(obj->parameters, "type"); - if (type == NULL) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Configuration object '%s' has no type.", - obj->object))); - error_count++; - } - else if (!strcmp(type, "service")) - { - char *router = config_get_value(obj->parameters, - "router"); - if (router) - { - char* max_slave_conn_str; - char* max_slave_rlag_str; - char *user; - char *auth; - char *enable_root_user; - char *connection_timeout; - char *auth_all_servers; - char *optimize_wildcard; - char *strip_db_esc; - char *weightby; - char *version_string; - char *subservices; - char *ssl,*ssl_cert,*ssl_key,*ssl_ca_cert,*ssl_version; - char* ssl_cert_verify_depth; - bool is_rwsplit = false; - bool is_schemarouter = false; - char *allow_localhost_match_wildcard_host; + * Process the data and create the services and servers defined + * in the data. + */ + obj = context; + while (obj) + { + char *type = config_get_value(obj->parameters, "type"); + if (type == NULL) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Configuration object '%s' has no type.", + obj->object))); + error_count++; + } + else if (!strcmp(type, "service")) + { + char *router = config_get_value(obj->parameters, "router"); + if (router) + { + char* max_slave_conn_str; + char* max_slave_rlag_str; + char *user; + char *auth; + char *enable_root_user; + char *connection_timeout; + char *auth_all_servers; + char *optimize_wildcard; + char *strip_db_esc; + char *weightby; + char *version_string; + char *subservices; + char *ssl, *ssl_cert, *ssl_key, *ssl_ca_cert, *ssl_version; + char* ssl_cert_verify_depth; + bool is_rwsplit = false; + bool is_schemarouter = false; + char *allow_localhost_match_wildcard_host; - obj->element = service_alloc(obj->object, router); - user = config_get_value(obj->parameters, "user"); - auth = config_get_value(obj->parameters, "passwd"); - subservices = config_get_value(obj->parameters, "subservices"); - ssl = config_get_value(obj->parameters, "ssl"); - ssl_cert = config_get_value(obj->parameters, "ssl_cert"); - ssl_key = config_get_value(obj->parameters, "ssl_key"); - ssl_ca_cert = config_get_value(obj->parameters, "ssl_ca_cert"); - ssl_version = config_get_value(obj->parameters, "ssl_version"); - ssl_cert_verify_depth = config_get_value(obj->parameters, "ssl_cert_verify_depth"); - enable_root_user = config_get_value( - obj->parameters, - "enable_root_user"); + obj->element = service_alloc(obj->object, router); + user = config_get_value(obj->parameters, "user"); + auth = config_get_value(obj->parameters, "passwd"); + subservices = config_get_value(obj->parameters, "subservices"); + ssl = config_get_value(obj->parameters, "ssl"); + ssl_cert = config_get_value(obj->parameters, "ssl_cert"); + ssl_key = config_get_value(obj->parameters, "ssl_key"); + ssl_ca_cert = config_get_value(obj->parameters, "ssl_ca_cert"); + ssl_version = config_get_value(obj->parameters, "ssl_version"); + ssl_cert_verify_depth = config_get_value(obj->parameters, "ssl_cert_verify_depth"); + enable_root_user = config_get_value(obj->parameters, "enable_root_user"); + connection_timeout = config_get_value(obj->parameters, "connection_timeout"); + optimize_wildcard = config_get_value(obj->parameters, "optimize_wildcard"); + auth_all_servers = config_get_value(obj->parameters, "auth_all_servers"); + strip_db_esc = config_get_value(obj->parameters, "strip_db_esc"); + allow_localhost_match_wildcard_host = config_get_value(obj->parameters, + "localhost_match_wildcard_host"); + weightby = config_get_value(obj->parameters, "weightby"); - connection_timeout = - config_get_value( - obj->parameters, - "connection_timeout"); + version_string = config_get_value(obj->parameters, "version_string"); - optimize_wildcard = - config_get_value( - obj->parameters, - "optimize_wildcard"); - - auth_all_servers = - config_get_value( - obj->parameters, - "auth_all_servers"); - - strip_db_esc = - config_get_value( - obj->parameters, - "strip_db_esc"); - - allow_localhost_match_wildcard_host = - config_get_value(obj->parameters, - "localhost_match_wildcard_host"); - - weightby = config_get_value(obj->parameters, "weightby"); - - version_string = config_get_value(obj->parameters, - "version_string"); - - if(subservices) - { - service_set_param_value(obj->element, - obj->parameters, - subservices, - 1,STRING_TYPE); - } - char *log_auth_warnings = config_get_value(obj->parameters, - "log_auth_warnings"); + if (subservices) + { + service_set_param_value(obj->element, + obj->parameters, + subservices, + 1, STRING_TYPE); + } + char *log_auth_warnings = config_get_value(obj->parameters, "log_auth_warnings"); int truthval; if (log_auth_warnings && (truthval = config_truth_value(log_auth_warnings)) != -1) { @@ -508,963 +514,992 @@ process_config_context(CONFIG_CONTEXT *context) } CONFIG_PARAMETER* param; - if((param = config_get_param(obj->parameters, "ignore_databases"))) + if ((param = config_get_param(obj->parameters, "ignore_databases"))) { service_set_param_value(obj->element, param, param->value, 0, STRING_TYPE); } - if((param = config_get_param(obj->parameters, "ignore_databases_regex"))) + if ((param = config_get_param(obj->parameters, "ignore_databases_regex"))) { service_set_param_value(obj->element, param, param->value, 0, STRING_TYPE); } - /** flag for rwsplit-specific parameters */ - if (strncmp(router, "readwritesplit", strlen("readwritesplit")+1) == 0) - { - is_rwsplit = true; - } + /** flag for rwsplit-specific parameters */ + if (strncmp(router, "readwritesplit", strlen("readwritesplit")+1) == 0) + { + is_rwsplit = true; + } - allow_localhost_match_wildcard_host = - config_get_value(obj->parameters, "localhost_match_wildcard_host"); + allow_localhost_match_wildcard_host = + config_get_value(obj->parameters, "localhost_match_wildcard_host"); - if (obj->element == NULL) /*< if module load failed */ + if (obj->element == NULL) /*< if module load failed */ + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Reading configuration " + "for router service '%s' failed. " + "Router %s is not loaded.", + obj->object, + obj->object))); + obj = obj->next; + continue; /*< process next obj */ + } + + if (version_string) { + /** Add the 5.5.5- string to the start of the version string if + * the version string starts with "10.". + * This mimics MariaDB 10.0 replication which adds 5.5.5- for backwards compatibility. */ + if (strncmp(version_string, "10.", 3) == 0) + { + ((SERVICE *)(obj->element))->version_string = + malloc((strlen(version_string) + strlen("5.5.5-") + 1) * sizeof(char)); + strcpy(((SERVICE *)(obj->element))->version_string, "5.5.5-"); + strcat(((SERVICE *)(obj->element))->version_string, version_string); + } + else + { + ((SERVICE *)(obj->element))->version_string = strdup(version_string); + } + } + else + { + if (gateway.version_string) + ((SERVICE *)(obj->element))->version_string = strdup(gateway.version_string); + } + + max_slave_conn_str = config_get_value(obj->parameters, "max_slave_connections"); + max_slave_rlag_str = config_get_value(obj->parameters, "max_slave_replication_lag"); + + if (ssl) + { + if (ssl_cert == NULL) + { + error_count++; + skygw_log_write(LE, "Error: Server certificate missing for service '%s'." + "Please provide the path to the server certificate by adding " + "the ssl_cert= parameter", obj->object); + } + + if (ssl_ca_cert == NULL) + { + error_count++; + skygw_log_write(LE, "Error: CA Certificate missing for service '%s'." + "Please provide the path to the certificate authority " + "certificate by adding the ssl_ca_cert= parameter", + obj->object); + } + + if (ssl_key == NULL) + { + error_count++; + skygw_log_write(LE, "Error: Server private key missing for service '%s'. " + "Please provide the path to the server certificate key by " + "adding the ssl_key= parameter", + obj->object); + } + + if (access(ssl_ca_cert, F_OK) != 0) + { + skygw_log_write(LE, "Error: Certificate authority file for service '%s' " + "not found: %s", + obj->object, ssl_ca_cert); + error_count++; + } + + if (access(ssl_cert, F_OK) != 0) + { + skygw_log_write(LE, "Error: Server certificate file for service '%s' not found: %s", + obj->object, + ssl_cert); + error_count++; + } + + if (access(ssl_key, F_OK) != 0) + { + skygw_log_write(LE, "Error: Server private key file for service '%s' not found: %s", + obj->object, + ssl_key); + error_count++; + } + + if (error_count == 0) + { + if (serviceSetSSL(obj->element, ssl) != 0) + { + skygw_log_write(LE, "Error: Unknown parameter for service '%s': %s", + obj->object, ssl); + error_count++; + } + else + { + serviceSetCertificates(obj->element, ssl_cert, ssl_key, ssl_ca_cert); + if (ssl_version) + { + if (serviceSetSSLVersion(obj->element, ssl_version) != 0) { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Reading configuration " - "for router service '%s' failed. " - "Router %s is not loaded.", - obj->object, - obj->object))); - obj = obj->next; - continue; /*< process next obj */ + skygw_log_write(LE, "Error: Unknown parameter value for " + "'ssl_version' for service '%s': %s", + obj->object, ssl_version); + error_count++; } - - if (version_string) { - - /** Add the 5.5.5- string to the start of the version string if - * the version string starts with "10.". - * This mimics MariaDB 10.0 replication which adds 5.5.5- for backwards compatibility. */ - if(strncmp(version_string,"10.",3) == 0) - { - ((SERVICE *)(obj->element))->version_string = malloc((strlen(version_string) + - strlen("5.5.5-") + 1) * sizeof(char)); - strcpy(((SERVICE *)(obj->element))->version_string,"5.5.5-"); - strcat(((SERVICE *)(obj->element))->version_string,version_string); - } - else - { - ((SERVICE *)(obj->element))->version_string = strdup(version_string); - } - } else { - if (gateway.version_string) - ((SERVICE *)(obj->element))->version_string = strdup(gateway.version_string); - } - max_slave_conn_str = - config_get_value(obj->parameters, - "max_slave_connections"); - - max_slave_rlag_str = - config_get_value(obj->parameters, - "max_slave_replication_lag"); - - if(ssl) - { - if(ssl_cert == NULL) - { - error_count++; - skygw_log_write(LE,"Error: Server certificate missing for service '%s'." - "Please provide the path to the server certificate by adding the ssl_cert= parameter", - obj->object); - } - if(ssl_ca_cert == NULL) - { - error_count++; - skygw_log_write(LE,"Error: CA Certificate missing for service '%s'." - "Please provide the path to the certificate authority certificate by adding the ssl_ca_cert= parameter", - obj->object); - } - if(ssl_key == NULL) - { - error_count++; - skygw_log_write(LE,"Error: Server private key missing for service '%s'. " - "Please provide the path to the server certificate key by adding the ssl_key= parameter" - ,obj->object); - } - - if(access(ssl_ca_cert,F_OK) != 0) - { - skygw_log_write(LE,"Error: Certificate authority file for service '%s' not found: %s", - obj->object, - ssl_ca_cert); - error_count++; - } - if(access(ssl_cert,F_OK) != 0) - { - skygw_log_write(LE,"Error: Server certificate file for service '%s' not found: %s", - obj->object, - ssl_cert); - error_count++; - } - if(access(ssl_key,F_OK) != 0) - { - skygw_log_write(LE,"Error: Server private key file for service '%s' not found: %s", - obj->object, - ssl_key); - error_count++; - } - - if(error_count == 0) - { - if(serviceSetSSL(obj->element,ssl) != 0) - { - skygw_log_write(LE,"Error: Unknown parameter for service '%s': %s",obj->object,ssl); - error_count++; - } - else - { - serviceSetCertificates(obj->element,ssl_cert,ssl_key,ssl_ca_cert); - if(ssl_version) - { - if(serviceSetSSLVersion(obj->element,ssl_version) != 0) - { - skygw_log_write(LE,"Error: Unknown parameter value for 'ssl_version' for service '%s': %s",obj->object,ssl_version); - error_count++; - } - } - if(ssl_cert_verify_depth) - { - if(serviceSetSSLVerifyDepth(obj->element,atoi(ssl_cert_verify_depth)) != 0) - { - skygw_log_write(LE,"Error: Invalid parameter value for 'ssl_cert_verify_depth' for service '%s': %s",obj->object,ssl_cert_verify_depth); - error_count++; - } - } - } - } - - } + } + if (ssl_cert_verify_depth) + { + if (serviceSetSSLVerifyDepth(obj->element, atoi(ssl_cert_verify_depth)) != 0) + { + skygw_log_write(LE, "Error: Invalid parameter value for " + "'ssl_cert_verify_depth' for service '%s': %s", + obj->object, ssl_cert_verify_depth); + error_count++; + } + } + } + } + } serviceSetRetryOnFailure(obj->element, config_get_value(obj->parameters, "retry_on_failure")); if (enable_root_user) - serviceEnableRootUser( - obj->element, - config_truth_value(enable_root_user)); + { + serviceEnableRootUser(obj->element, config_truth_value(enable_root_user)); + } - if (connection_timeout) - serviceSetTimeout( - obj->element, - atoi(connection_timeout)); + if (connection_timeout) + { + serviceSetTimeout(obj->element, atoi(connection_timeout)); + } - if(auth_all_servers) - serviceAuthAllServers(obj->element, - config_truth_value(auth_all_servers)); + if(auth_all_servers) + { + serviceAuthAllServers(obj->element, config_truth_value(auth_all_servers)); + } - if(optimize_wildcard) - serviceOptimizeWildcard(obj->element, - config_truth_value(optimize_wildcard)); + if(optimize_wildcard) + { + serviceOptimizeWildcard(obj->element, config_truth_value(optimize_wildcard)); + } - if(strip_db_esc) - serviceStripDbEsc(obj->element, - config_truth_value(strip_db_esc)); + if(strip_db_esc) + { + serviceStripDbEsc(obj->element, config_truth_value(strip_db_esc)); + } - if (weightby) - serviceWeightBy(obj->element, weightby); + if (weightby) + { + serviceWeightBy(obj->element, weightby); + } - if (allow_localhost_match_wildcard_host) - serviceEnableLocalhostMatchWildcardHost( - obj->element, - config_truth_value(allow_localhost_match_wildcard_host)); + if (allow_localhost_match_wildcard_host) + { + serviceEnableLocalhostMatchWildcardHost( + obj->element, + config_truth_value(allow_localhost_match_wildcard_host)); + } - if (!auth) - auth = config_get_value(obj->parameters, - "auth"); + if (!auth) + { + auth = config_get_value(obj->parameters, "auth"); + } - if (obj->element && user && auth) - { - serviceSetUser(obj->element, - user, - auth); - } - else if (user && auth == NULL) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Service '%s' has a " - "user defined but no " - "corresponding password.", - obj->object))); - } - /** Read, validate and set max_slave_connections */ - if (max_slave_conn_str != NULL) - { - CONFIG_PARAMETER* param; - bool succp; - - param = config_get_param(obj->parameters, - "max_slave_connections"); - - if (param == NULL) - { - succp = false; - } - else - { - succp = service_set_param_value( - obj->element, - param, - max_slave_conn_str, - COUNT_ATMOST, - (COUNT_TYPE|PERCENT_TYPE)); - } - - if (!succp) - { - LOGIF(LM, (skygw_log_write( - LOGFILE_MESSAGE, - "* Warning : invalid value type " - "for parameter \'%s.%s = %s\'\n\tExpected " - "type is either for slave connection " - "count or\n\t%% for specifying the " - "maximum percentage of available the " - "slaves that will be connected.", - ((SERVICE*)obj->element)->name, - param->name, - param->value))); - } - } - /** Read, validate and set max_slave_replication_lag */ - if (max_slave_rlag_str != NULL) - { - CONFIG_PARAMETER* param; - bool succp; - - param = config_get_param( - obj->parameters, - "max_slave_replication_lag"); - - if (param == NULL) - { - succp = false; - } - else - { - succp = service_set_param_value( - obj->element, - param, - max_slave_rlag_str, - COUNT_ATMOST, - COUNT_TYPE); - } - - if (!succp) - { - LOGIF(LM, (skygw_log_write( - LOGFILE_MESSAGE, - "* Warning : invalid value type " - "for parameter \'%s.%s = %s\'\n\tExpected " - "type is for maximum " - "slave replication lag.", - ((SERVICE*)obj->element)->name, - param->name, - param->value))); - } - } - /** Parameters for rwsplit router only */ - if (is_rwsplit) - { - CONFIG_PARAMETER* param; - char* use_sql_variables_in; - bool succp; - - use_sql_variables_in = - config_get_value(obj->parameters, - "use_sql_variables_in"); - - if (use_sql_variables_in != NULL) - { - param = config_get_param( - obj->parameters, - "use_sql_variables_in"); - - if (param == NULL) - { - succp = false; - } - else - { - succp = service_set_param_value(obj->element, - param, - use_sql_variables_in, - COUNT_NONE, - SQLVAR_TARGET_TYPE); - } - - if (!succp) - { - if(param){ - LOGIF(LM, (skygw_log_write( - LOGFILE_MESSAGE, - "* Warning : invalid value type " - "for parameter \'%s.%s = %s\'\n\tExpected " - "type is [master|all] for " - "use sql variables in.", - ((SERVICE*)obj->element)->name, - param->name, - param->value))); - }else{ - LOGIF(LE, (skygw_log_write( - LOGFILE_ERROR, - "Error : parameter was NULL"))); - - } - } - } - } /*< if (rw_split) */ - } /*< if (router) */ - else - { - obj->element = NULL; - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : No router defined for service " - "'%s'\n", - obj->object))); - error_count++; - } - } - else if (!strcmp(type, "server")) - { - char *address; - char *port; - char *protocol; - char *monuser; - char *monpw; + if (obj->element && user && auth) + { + serviceSetUser(obj->element, user, auth); + } + else if (user && auth == NULL) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Service '%s' has a " + "user defined but no " + "corresponding password.", + obj->object))); + } + /** Read, validate and set max_slave_connections */ + if (max_slave_conn_str != NULL) + { + CONFIG_PARAMETER* param; + bool succp; - address = config_get_value(obj->parameters, "address"); - port = config_get_value(obj->parameters, "port"); - protocol = config_get_value(obj->parameters, "protocol"); - monuser = config_get_value(obj->parameters, - "monitoruser"); - monpw = config_get_value(obj->parameters, "monitorpw"); + param = config_get_param(obj->parameters, "max_slave_connections"); - if (address && port && protocol) - { - obj->element = server_alloc(address, - protocol, - atoi(port)); - server_set_unique_name(obj->element, obj->object); - } - else - { - obj->element = NULL; - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Server '%s' is missing a " - "required configuration parameter. A " - "server must " - "have address, port and protocol " - "defined.", - obj->object))); - error_count++; - } - if (obj->element && monuser && monpw) - serverAddMonUser(obj->element, monuser, monpw); - else if (monuser && monpw == NULL) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Server '%s' has a monitoruser" - "defined but no corresponding password.", - obj->object))); - } - if (obj->element) - { - SERVER *server = obj->element; - server->persistpoolmax = strtol(config_get_value_string(obj->parameters, "persistpoolmax"), NULL, 0); - server->persistmaxtime = strtol(config_get_value_string(obj->parameters, "persistmaxtime"), NULL, 0); - CONFIG_PARAMETER *params = obj->parameters; - while (params) - { - if (strcmp(params->name, "address") - && strcmp(params->name, "port") - && strcmp(params->name, - "protocol") - && strcmp(params->name, - "monitoruser") - && strcmp(params->name, - "monitorpw") - && strcmp(params->name, - "type") - && strcmp(params->name, - "persistpoolmax") - && strcmp(params->name, - "persistmaxtime") - ) - { - serverAddParameter(obj->element, - params->name, - params->value); - } - params = params->next; - } - } - } - else if (!strcmp(type, "filter")) - { - char *module = config_get_value(obj->parameters, - "module"); - char *options = config_get_value(obj->parameters, - "options"); + if (param == NULL) + { + succp = false; + } + else + { + succp = service_set_param_value( + obj->element, + param, + max_slave_conn_str, + COUNT_ATMOST, + (COUNT_TYPE|PERCENT_TYPE)); + } - if (module) - { - obj->element = filter_alloc(obj->object, module); - } - else - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error: Filter '%s' has no module " - "defined defined to load.", - obj->object))); - error_count++; - } - if (obj->element && options) - { - char *lasts; - char *s = strtok_r(options, ",", &lasts); - while (s) - { - filterAddOption(obj->element, s); - s = strtok_r(NULL, ",", &lasts); - } - } - if (obj->element) - { - CONFIG_PARAMETER *params = obj->parameters; - while (params) - { - if (strcmp(params->name, "module") - && strcmp(params->name, - "options")) - { - filterAddParameter(obj->element, - params->name, - params->value); - } - params = params->next; - } - } - } - obj = obj->next; - } + if (!succp) + { + LOGIF(LM, (skygw_log_write( + LOGFILE_MESSAGE, + "* Warning : invalid value type " + "for parameter \'%s.%s = %s\'\n\tExpected " + "type is either for slave connection " + "count or\n\t%% for specifying the " + "maximum percentage of available the " + "slaves that will be connected.", + ((SERVICE*)obj->element)->name, + param->name, + param->value))); + } + } + /** Read, validate and set max_slave_replication_lag */ + if (max_slave_rlag_str != NULL) + { + CONFIG_PARAMETER* param; + bool succp; - /* - * Now we have the services we can add the servers to the services - * add the protocols to the services - */ - obj = context; - while (obj) - { - char *type = config_get_value(obj->parameters, "type"); - if (type == NULL) - ; - else if (!strcmp(type, "service")) - { - char *servers; - char *roptions; - char *router; - char *filters = config_get_value(obj->parameters, - "filters"); - servers = config_get_value(obj->parameters, "servers"); - roptions = config_get_value(obj->parameters, - "router_options"); - router = config_get_value(obj->parameters, "router"); - if (servers && obj->element) - { - char *lasts; - char *s = strtok_r(servers, ",", &lasts); - while (s) - { - CONFIG_CONTEXT *obj1 = context; - int found = 0; - while (obj1) - { - if (strcmp(trim(s), obj1->object) == 0 && - obj->element && obj1->element) - { - found = 1; - serviceAddBackend( - obj->element, - obj1->element); - } - obj1 = obj1->next; - } - if (!found) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error: Unable to find " - "server '%s' that is " - "configured as part of " - "service '%s'.", - s, obj->object))); - } - s = strtok_r(NULL, ",", &lasts); - } - } - else if (servers == NULL && !isInternalService(router)) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Warning: The service '%s' is missing a " - "definition of the servers that provide " - "the service.", - obj->object))); - } - if (roptions && obj->element) - { - char *lasts; - char *s = strtok_r(roptions, ",", &lasts); - while (s) - { - serviceAddRouterOption(obj->element, s); - s = strtok_r(NULL, ",", &lasts); - } - } - if (filters && obj->element) - { - serviceSetFilters(obj->element, filters); - } - } - else if (!strcmp(type, "listener")) - { - char *service; - char *address; - char *port; - char *protocol; - char *socket; - struct sockaddr_in serv_addr; + param = config_get_param( + obj->parameters, + "max_slave_replication_lag"); - service = config_get_value(obj->parameters, "service"); - port = config_get_value(obj->parameters, "port"); - address = config_get_value(obj->parameters, "address"); - protocol = config_get_value(obj->parameters, "protocol"); - socket = config_get_value(obj->parameters, "socket"); + if (param == NULL) + { + succp = false; + } + else + { + succp = service_set_param_value( + obj->element, + param, + max_slave_rlag_str, + COUNT_ATMOST, + COUNT_TYPE); + } - /* if id is not set, do it now */ - if (gateway.id == 0) { - setipaddress(&serv_addr.sin_addr, (address == NULL) ? "0.0.0.0" : address); - gateway.id = (unsigned long) (serv_addr.sin_addr.s_addr + (port != NULL ? atoi(port) : 0 + getpid())); - } + if (!succp) + { + LOGIF(LM, (skygw_log_write( + LOGFILE_MESSAGE, + "* Warning : invalid value type " + "for parameter \'%s.%s = %s\'\n\tExpected " + "type is for maximum " + "slave replication lag.", + ((SERVICE*)obj->element)->name, + param->name, + param->value))); + } + } + /** Parameters for rwsplit router only */ + if (is_rwsplit) + { + CONFIG_PARAMETER* param; + char* use_sql_variables_in; + bool succp; - if(service && protocol && (socket || port)) - { - if (socket) - { - CONFIG_CONTEXT *ptr = context; - while (ptr && strcmp(ptr->object, service) != 0) - ptr = ptr->next; - if (ptr && ptr->element) - { - serviceAddProtocol(ptr->element, - protocol, - socket, - 0); - } - else - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Listener '%s', " - "service '%s' not found. " - "Listener will not execute for socket %s.", - obj->object, service, socket))); - error_count++; - } - } + use_sql_variables_in = + config_get_value(obj->parameters, "use_sql_variables_in"); - if (port) - { - CONFIG_CONTEXT *ptr = context; - while (ptr && strcmp(ptr->object, service) != 0) - ptr = ptr->next; - if (ptr && ptr->element) - { - serviceAddProtocol(ptr->element, - protocol, - address, - atoi(port)); - } - else - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Listener '%s', " - "service '%s' not found. " - "Listener will not execute.", - obj->object, service))); - error_count++; - } - } - } - else - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Listener '%s' is missing a " - "required " - "parameter. A Listener must have a " - "service, port and protocol defined.", - obj->object))); - error_count++; - } - } - else if (!strcmp(type, "monitor")) - { - char *module; - char *servers; - char *user; - char *passwd; - unsigned long interval = 0; - int connect_timeout = 0; - int read_timeout = 0; - int write_timeout = 0; + if (use_sql_variables_in != NULL) + { + param = config_get_param(obj->parameters, + "use_sql_variables_in"); - module = config_get_value(obj->parameters, "module"); - servers = config_get_value(obj->parameters, "servers"); - user = config_get_value(obj->parameters, "user"); - passwd = config_get_value(obj->parameters, "passwd"); - if (config_get_value(obj->parameters, "monitor_interval")) { - interval = strtoul(config_get_value(obj->parameters, "monitor_interval"), NULL, 10); - } + if (param == NULL) + { + succp = false; + } + else + { + succp = service_set_param_value(obj->element, + param, + use_sql_variables_in, + COUNT_NONE, + SQLVAR_TARGET_TYPE); + } - if (config_get_value(obj->parameters, "backend_connect_timeout")) { - connect_timeout = atoi(config_get_value(obj->parameters, "backend_connect_timeout")); - } - if (config_get_value(obj->parameters, "backend_read_timeout")) { - read_timeout = atoi(config_get_value(obj->parameters, "backend_read_timeout")); - } - if (config_get_value(obj->parameters, "backend_write_timeout")) { - write_timeout = atoi(config_get_value(obj->parameters, "backend_write_timeout")); - } - - if (module) - { - obj->element = monitor_alloc(obj->object, module); - if (servers && obj->element) - { - char *s, *lasts; + if (!succp) + { + if(param) + { + LOGIF(LM, (skygw_log_write( + LOGFILE_MESSAGE, + "* Warning : invalid value type " + "for parameter \'%s.%s = %s\'\n\tExpected " + "type is [master|all] for " + "use sql variables in.", + ((SERVICE*)obj->element)->name, + param->name, + param->value))); + } + else + { + LOGIF(LE, (skygw_log_write( + LOGFILE_ERROR, + "Error : parameter was NULL"))); + } + } + } + } /*< if (rw_split) */ + } /*< if (router) */ + else + { + obj->element = NULL; + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : No router defined for service " + "'%s'\n", + obj->object))); + error_count++; + } + } + else if (!strcmp(type, "server")) + { + char *address; + char *port; + char *protocol; + char *monuser; + char *monpw; - /* if id is not set, compute it now with pid only */ - if (gateway.id == 0) { - gateway.id = getpid(); - } + address = config_get_value(obj->parameters, "address"); + port = config_get_value(obj->parameters, "port"); + protocol = config_get_value(obj->parameters, "protocol"); + monuser = config_get_value(obj->parameters, "monitoruser"); + monpw = config_get_value(obj->parameters, "monitorpw"); + + if (address && port && protocol) + { + obj->element = server_alloc(address, + protocol, + atoi(port)); + server_set_unique_name(obj->element, obj->object); + } + else + { + obj->element = NULL; + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Server '%s' is missing a " + "required configuration parameter. A " + "server must " + "have address, port and protocol " + "defined.", + obj->object))); + error_count++; + } + + if (obj->element && monuser && monpw) + { + serverAddMonUser(obj->element, monuser, monpw); + } + else if (monuser && monpw == NULL) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Server '%s' has a monitoruser" + "defined but no corresponding password.", + obj->object))); + } + + if (obj->element) + { + SERVER *server = obj->element; + server->persistpoolmax = strtol(config_get_value_string(obj->parameters, + "persistpoolmax"), NULL, 0); + server->persistmaxtime = strtol(config_get_value_string(obj->parameters, + "persistmaxtime"), NULL, 0); + CONFIG_PARAMETER *params = obj->parameters; + + while (params) + { + if (strcmp(params->name, "address") + && strcmp(params->name, "port") + && strcmp(params->name, "protocol") + && strcmp(params->name, "monitoruser") + && strcmp(params->name, "monitorpw") + && strcmp(params->name, "type") + && strcmp(params->name, "persistpoolmax") + && strcmp(params->name, "persistmaxtime")) + { + serverAddParameter(obj->element, params->name, params->value); + } + params = params->next; + } + } + } + else if (!strcmp(type, "filter")) + { + char *module = config_get_value(obj->parameters, "module"); + char *options = config_get_value(obj->parameters, "options"); + + if (module) + { + obj->element = filter_alloc(obj->object, module); + } + else + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error: Filter '%s' has no module " + "defined defined to load.", + obj->object))); + error_count++; + } + + if (obj->element && options) + { + char *lasts; + char *s = strtok_r(options, ",", &lasts); + while (s) + { + filterAddOption(obj->element, s); + s = strtok_r(NULL, ",", &lasts); + } + } + + if (obj->element) + { + CONFIG_PARAMETER *params = obj->parameters; + while (params) + { + if (strcmp(params->name, "module") && strcmp(params->name, "options")) + { + filterAddParameter(obj->element, + params->name, + params->value); + } + params = params->next; + } + } + } + obj = obj->next; + } + + /* + * Now we have the services we can add the servers to the services + * add the protocols to the services + */ + obj = context; + while (obj) + { + char *type = config_get_value(obj->parameters, "type"); + if (type == NULL) + { + ; + } + else if (!strcmp(type, "service")) + { + char *servers; + char *roptions; + char *router; + char *filters = config_get_value(obj->parameters, "filters"); + servers = config_get_value(obj->parameters, "servers"); + roptions = config_get_value(obj->parameters, "router_options"); + router = config_get_value(obj->parameters, "router"); + if (servers && obj->element) + { + char *lasts; + char *s = strtok_r(servers, ",", &lasts); + while (s) + { + CONFIG_CONTEXT *obj1 = context; + int found = 0; + while (obj1) + { + if (strcmp(trim(s), obj1->object) == 0 && obj->element && obj1->element) + { + found = 1; + serviceAddBackend(obj->element, obj1->element); + } + obj1 = obj1->next; + } + + if (!found) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error: Unable to find " + "server '%s' that is " + "configured as part of " + "service '%s'.", + s, obj->object))); + } + s = strtok_r(NULL, ",", &lasts); + } + } + else if (servers == NULL && !isInternalService(router)) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Warning: The service '%s' is missing a " + "definition of the servers that provide " + "the service.", + obj->object))); + } + + if (roptions && obj->element) + { + char *lasts; + char *s = strtok_r(roptions, ",", &lasts); + while (s) + { + serviceAddRouterOption(obj->element, s); + s = strtok_r(NULL, ",", &lasts); + } + } + + if (filters && obj->element) + { + serviceSetFilters(obj->element, filters); + } + } + else if (!strcmp(type, "listener")) + { + char *service; + char *address; + char *port; + char *protocol; + char *socket; + struct sockaddr_in serv_addr; + + service = config_get_value(obj->parameters, "service"); + port = config_get_value(obj->parameters, "port"); + address = config_get_value(obj->parameters, "address"); + protocol = config_get_value(obj->parameters, "protocol"); + socket = config_get_value(obj->parameters, "socket"); + + /* if id is not set, do it now */ + if (gateway.id == 0) + { + setipaddress(&serv_addr.sin_addr, (address == NULL) ? "0.0.0.0" : address); + gateway.id = (unsigned long) (serv_addr.sin_addr.s_addr + + (port != NULL ? atoi(port) : 0 + getpid())); + } + + if (service && protocol && (socket || port)) + { + if (socket) + { + CONFIG_CONTEXT *ptr = context; + while (ptr && strcmp(ptr->object, service) != 0) + { + ptr = ptr->next; + } + + if (ptr && ptr->element) + { + serviceAddProtocol(ptr->element, protocol, socket, 0); + } + else + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Listener '%s', " + "service '%s' not found. " + "Listener will not execute for socket %s.", + obj->object, service, socket))); + error_count++; + } + } + + if (port) + { + CONFIG_CONTEXT *ptr = context; + while (ptr && strcmp(ptr->object, service) != 0) + { + ptr = ptr->next; + } + + if (ptr && ptr->element) + { + serviceAddProtocol(ptr->element, protocol, address, atoi(port)); + } + else + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Listener '%s', " + "service '%s' not found. " + "Listener will not execute.", + obj->object, service))); + error_count++; + } + } + } + else + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Listener '%s' is missing a " + "required " + "parameter. A Listener must have a " + "service, port and protocol defined.", + obj->object))); + error_count++; + } + } + else if (!strcmp(type, "monitor")) + { + char *module; + char *servers; + char *user; + char *passwd; + unsigned long interval = 0; + int connect_timeout = 0; + int read_timeout = 0; + int write_timeout = 0; + + module = config_get_value(obj->parameters, "module"); + servers = config_get_value(obj->parameters, "servers"); + user = config_get_value(obj->parameters, "user"); + passwd = config_get_value(obj->parameters, "passwd"); + if (config_get_value(obj->parameters, "monitor_interval")) + { + interval = strtoul(config_get_value(obj->parameters, "monitor_interval"), NULL, 10); + } + + if (config_get_value(obj->parameters, "backend_connect_timeout")) + { + connect_timeout = atoi(config_get_value(obj->parameters, "backend_connect_timeout")); + } + if (config_get_value(obj->parameters, "backend_read_timeout")) + { + read_timeout = atoi(config_get_value(obj->parameters, "backend_read_timeout")); + } + if (config_get_value(obj->parameters, "backend_write_timeout")) + { + write_timeout = atoi(config_get_value(obj->parameters, "backend_write_timeout")); + } + + if (module) + { + obj->element = monitor_alloc(obj->object, module); + if (servers && obj->element) + { + char *s, *lasts; + + /* if id is not set, compute it now with pid only */ + if (gateway.id == 0) + { + gateway.id = getpid(); + } monitorAddParameters(obj->element, obj->parameters); - /* set monitor interval */ - if (interval > 0) - monitorSetInterval(obj->element, interval); - else - skygw_log_write(LOGFILE_ERROR,"Warning: Monitor '%s' " - "missing monitor_interval parameter, " - "default value of 10000 miliseconds.",obj->object); + /* set monitor interval */ + if (interval > 0) + { + monitorSetInterval(obj->element, interval); + } + else + { + skygw_log_write(LOGFILE_ERROR, "Warning: Monitor '%s' " + "missing monitor_interval parameter, " + "default value of 10000 miliseconds.", obj->object); + } - /* set timeouts */ - if (connect_timeout > 0) - monitorSetNetworkTimeout(obj->element, MONITOR_CONNECT_TIMEOUT, connect_timeout); - if (read_timeout > 0) - monitorSetNetworkTimeout(obj->element, MONITOR_READ_TIMEOUT, read_timeout); - if (write_timeout > 0) - monitorSetNetworkTimeout(obj->element, MONITOR_WRITE_TIMEOUT, write_timeout); + /* set timeouts */ + if (connect_timeout > 0) + { + monitorSetNetworkTimeout(obj->element, MONITOR_CONNECT_TIMEOUT, connect_timeout); + } + if (read_timeout > 0) + { + monitorSetNetworkTimeout(obj->element, MONITOR_READ_TIMEOUT, read_timeout); + } + if (write_timeout > 0) + { + monitorSetNetworkTimeout(obj->element, MONITOR_WRITE_TIMEOUT, write_timeout); + } - /* get the servers to monitor */ - s = strtok_r(servers, ",", &lasts); - while (s) - { - CONFIG_CONTEXT *obj1 = context; - int found = 0; - while (obj1) - { - if (strcmp(trim(s), obj1->object) == 0 && - obj->element && obj1->element) - { - found = 1; - if(hashtable_add(monitorhash,obj1->object,"") == 0) - { - skygw_log_write(LOGFILE_ERROR, - "Warning: Multiple monitors are monitoring server [%s]. " - "This will cause undefined behavior.", - obj1->object); - } - monitorAddServer( - obj->element, - obj1->element); - } - obj1 = obj1->next; - } - if (!found) - LOGIF(LE, - (skygw_log_write_flush( - LOGFILE_ERROR, - "Error: Unable to find " - "server '%s' that is " - "configured in the " - "monitor '%s'.", - s, obj->object))); + /* get the servers to monitor */ + s = strtok_r(servers, ",", &lasts); + while (s) + { + CONFIG_CONTEXT *obj1 = context; + int found = 0; + while (obj1) + { + if (strcmp(trim(s), obj1->object) == 0 && obj->element && obj1->element) + { + found = 1; + if (hashtable_add(monitorhash, obj1->object, "") == 0) + { + skygw_log_write(LOGFILE_ERROR, + "Warning: Multiple monitors are monitoring server [%s]. " + "This will cause undefined behavior.", + obj1->object); + } + monitorAddServer(obj->element, obj1->element); + } + obj1 = obj1->next; + } + if (!found) + { + LOGIF(LE, + (skygw_log_write_flush( + LOGFILE_ERROR, + "Error: Unable to find " + "server '%s' that is " + "configured in the " + "monitor '%s'.", + s, obj->object))); + } - s = strtok_r(NULL, ",", &lasts); - } - } - if (obj->element && user && passwd) - { - monitorAddUser(obj->element, - user, - passwd); - check_monitor_permissions(obj->element); - } - else if (obj->element && user) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, "Error: " - "Monitor '%s' defines a " - "username with no password.", - obj->object))); - error_count++; - } - } - else - { - obj->element = NULL; - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Monitor '%s' is missing a " - "require module parameter.", - obj->object))); - error_count++; - } - } - else if (strcmp(type, "server") != 0 - && strcmp(type, "filter") != 0) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Configuration object '%s' has an " - "invalid type specified.", - obj->object))); - error_count++; - } + s = strtok_r(NULL, ",", &lasts); + } + } - obj = obj->next; - } /*< while */ + if (obj->element && user && passwd) + { + monitorAddUser(obj->element, user, passwd); + check_monitor_permissions(obj->element); + } + else if (obj->element && user) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, "Error: " + "Monitor '%s' defines a " + "username with no password.", + obj->object))); + error_count++; + } + } + else + { + obj->element = NULL; + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Monitor '%s' is missing a " + "require module parameter.", + obj->object))); + error_count++; + } + } + else if (strcmp(type, "server") != 0 && strcmp(type, "filter") != 0) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Configuration object '%s' has an " + "invalid type specified.", + obj->object))); + error_count++; + } - /** TODO: consistency check function */ + obj = obj->next; + } /*< while */ - hashtable_free(monitorhash); - /** - * error_count += consistency_checks(); - */ + /** TODO: consistency check function */ - if (error_count) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : %d errors where encountered processing the " - "configuration file '%s'.", - error_count, - config_file))); - return 0; - } - return 1; + hashtable_free(monitorhash); + /** + * error_count += consistency_checks(); + */ + + if (error_count) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : %d errors where encountered processing the " + "configuration file '%s'.", + error_count, + config_file))); + return 0; + } + + return 1; } /** * Get the value of a config parameter * - * @param params The linked list of config parameters - * @param name The parameter to return + * @param params The linked list of config parameters + * @param name The parameter to return * @return the parameter value or NULL if not found */ static char * config_get_value(CONFIG_PARAMETER *params, const char *name) { - while (params) - { - if (!strcmp(params->name, name)) - return params->value; - params = params->next; - } - return NULL; + while (params) + { + if (!strcmp(params->name, name)) + { + return params->value; + } + + params = params->next; + } + return NULL; } /** * Get the value of a config parameter as a string * - * @param params The linked list of config parameters - * @param name The parameter to return + * @param params The linked list of config parameters + * @param name The parameter to return * @return the parameter value or null string if not found */ static const char * config_get_value_string(CONFIG_PARAMETER *params, const char *name) { - while (params) - { - if (!strcmp(params->name, name)) - return (const char *)params->value; - params = params->next; - } - return ""; + while (params) + { + if (!strcmp(params->name, name)) + { + return (const char *)params->value; + } + + params = params->next; + } + return ""; } CONFIG_PARAMETER* config_get_param( - CONFIG_PARAMETER* params, - const char* name) + CONFIG_PARAMETER* params, + const char* name) { - while (params) + while (params) + { + if (!strcmp(params->name, name)) { - if (!strcmp(params->name, name)) - return params; - params = params->next; + return params; } - return NULL; + + params = params->next; + } + return NULL; } config_param_type_t config_get_paramtype( - CONFIG_PARAMETER* param) + CONFIG_PARAMETER* param) { - return param->qfd_param_type; + return param->qfd_param_type; } bool config_get_valint( - int* val, - CONFIG_PARAMETER* param, - const char* name, /*< if NULL examine current param only */ - config_param_type_t ptype) -{ - bool succp = false;; - - ss_dassert((ptype == COUNT_TYPE || ptype == PERCENT_TYPE) && param != NULL); - - while (param) - { - if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) - { - switch (ptype) { - case COUNT_TYPE: - *val = param->qfd.valcount; - succp = true; - goto return_succp; - - case PERCENT_TYPE: - *val = param->qfd.valpercent; - succp =true; - goto return_succp; + int* val, + CONFIG_PARAMETER* param, + const char* name, /*< if NULL examine current param only */ + config_param_type_t ptype) +{ + bool succp = false;; - default: - goto return_succp; - } - } - param = param->next; + ss_dassert((ptype == COUNT_TYPE || ptype == PERCENT_TYPE) && param != NULL); + + while (param) + { + if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) + { + switch (ptype) { + case COUNT_TYPE: + *val = param->qfd.valcount; + succp = true; + goto return_succp; + + case PERCENT_TYPE: + *val = param->qfd.valpercent; + succp =true; + goto return_succp; + + default: + goto return_succp; + } } + param = param->next; + } return_succp: - return succp; + return succp; } bool config_get_valbool( - bool* val, - CONFIG_PARAMETER* param, - const char* name, - config_param_type_t ptype) + bool* val, + CONFIG_PARAMETER* param, + const char* name, + config_param_type_t ptype) { - bool succp; - - ss_dassert(ptype == BOOL_TYPE); - ss_dassert(param != NULL); - - if (ptype != BOOL_TYPE || param == NULL) - { - succp = false; - goto return_succp; - } - - while (param) - { - if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) - { - *val = param->qfd.valbool; - succp = true; - goto return_succp; - } - param = param->next; - } - succp = false; - + bool succp; + + ss_dassert(ptype == BOOL_TYPE); + ss_dassert(param != NULL); + + if (ptype != BOOL_TYPE || param == NULL) + { + succp = false; + goto return_succp; + } + + while (param) + { + if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) + { + *val = param->qfd.valbool; + succp = true; + goto return_succp; + } + param = param->next; + } + succp = false; + return_succp: - return succp; - + return succp; } bool config_get_valtarget( - target_t* val, - CONFIG_PARAMETER* param, - const char* name, - config_param_type_t ptype) + target_t* val, + CONFIG_PARAMETER* param, + const char* name, + config_param_type_t ptype) { - bool succp; - - ss_dassert(ptype == SQLVAR_TARGET_TYPE); - ss_dassert(param != NULL); - - if (ptype != SQLVAR_TARGET_TYPE || param == NULL) - { - succp = false; - goto return_succp; - } - - while (param) - { - if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) - { - *val = param->qfd.valtarget; - succp = true; - goto return_succp; - } - param = param->next; - } - succp = false; - + bool succp; + + ss_dassert(ptype == SQLVAR_TARGET_TYPE); + ss_dassert(param != NULL); + + if (ptype != SQLVAR_TARGET_TYPE || param == NULL) + { + succp = false; + goto return_succp; + } + + while (param) + { + if (name == NULL || !strncmp(param->name, name, MAX_PARAM_LEN)) + { + *val = param->qfd.valtarget; + succp = true; + goto return_succp; + } + param = param->next; + } + succp = false; + return_succp: - return succp; - + return succp; } CONFIG_PARAMETER* config_clone_param( - CONFIG_PARAMETER* param) + CONFIG_PARAMETER* param) { - CONFIG_PARAMETER* p2; - - p2 = (CONFIG_PARAMETER*) malloc(sizeof(CONFIG_PARAMETER)); - - if (p2 == NULL) - { - goto return_p2; - } - memcpy(p2, param, sizeof(CONFIG_PARAMETER)); - p2->name = strndup(param->name, MAX_PARAM_LEN); - p2->value = strndup(param->value, MAX_PARAM_LEN); - - if (param->qfd_param_type == STRING_TYPE) - { - p2->qfd.valstr = strndup(param->qfd.valstr, MAX_PARAM_LEN); - } - + CONFIG_PARAMETER* p2; + + p2 = (CONFIG_PARAMETER*) malloc(sizeof(CONFIG_PARAMETER)); + + if (p2 == NULL) + { + goto return_p2; + } + memcpy(p2, param, sizeof(CONFIG_PARAMETER)); + p2->name = strndup(param->name, MAX_PARAM_LEN); + p2->value = strndup(param->value, MAX_PARAM_LEN); + + if (param->qfd_param_type == STRING_TYPE) + { + p2->qfd.valstr = strndup(param->qfd.valstr, MAX_PARAM_LEN); + } + return_p2: - return p2; + return p2; } /** @@ -1486,22 +1521,22 @@ void free_config_parameter(CONFIG_PARAMETER* p1) /** * Free a config tree * - * @param context The configuration data + * @param context The configuration data */ -static void +static void free_config_context(CONFIG_CONTEXT *context) { -CONFIG_CONTEXT *obj; -CONFIG_PARAMETER *p1, *p2; + CONFIG_CONTEXT *obj; + CONFIG_PARAMETER *p1, *p2; - while (context) - { - free(context->object); - free_config_parameter(context->parameters); - obj = context->next; - free(context); - context = obj; - } + while (context) + { + free(context->object); + free_config_parameter(context->parameters); + obj = context->next; + free(context); + context = obj; + } } /** @@ -1512,7 +1547,7 @@ CONFIG_PARAMETER *p1, *p2; int config_threadcount() { - return gateway.n_threads; + return gateway.n_threads; } /** @@ -1524,7 +1559,7 @@ config_threadcount() unsigned int config_nbpolls() { - return gateway.n_nbpoll; + return gateway.n_nbpoll; } /** @@ -1536,7 +1571,7 @@ config_nbpolls() unsigned int config_pollsleep() { - return gateway.pollsleep; + return gateway.pollsleep; } /** @@ -1547,133 +1582,150 @@ config_pollsleep() FEEDBACK_CONF * config_get_feedback_data() { - return &feedback; + return &feedback; } -static struct { - char *logname; - logfile_id_t logfile; +static struct +{ + char *logname; + logfile_id_t logfile; } lognames[] = { - { "log_messages", LOGFILE_MESSAGE }, - { "log_trace", LOGFILE_TRACE }, - { "log_debug", LOGFILE_DEBUG }, - { NULL, 0 } + { "log_messages", LOGFILE_MESSAGE }, + { "log_trace", LOGFILE_TRACE }, + { "log_debug", LOGFILE_DEBUG }, + { NULL, 0 } }; /** * Configuration handler for items in the global [MaxScale] section * - * @param name The item name - * @param value The item value + * @param name The item name + * @param value The item value * @return 0 on error */ -static int +static int handle_global_item(const char *name, const char *value) { -int i; - if (strcmp(name, "threads") == 0) - { - int thrcount = atoi(value); - if (thrcount > 0) - { - gateway.n_threads = thrcount; - } - else - { - skygw_log_write(LE, "Warning: Invalid value for 'threads': %s.", value); - return 0; - } - } - else if (strcmp(name, "non_blocking_polls") == 0) - { - gateway.n_nbpoll = atoi(value); - } - else if (strcmp(name, "poll_sleep") == 0) - { - gateway.pollsleep = atoi(value); + int i; + if (strcmp(name, "threads") == 0) + { + int thrcount = atoi(value); + if (thrcount > 0) + { + gateway.n_threads = thrcount; } - else if (strcmp(name, "ms_timestamp") == 0) - { - skygw_set_highp(config_truth_value((char*)value)); - } + else + { + skygw_log_write(LE, "Warning: Invalid value for 'threads': %s.", value); + return 0; + } + } + else if (strcmp(name, "non_blocking_polls") == 0) + { + gateway.n_nbpoll = atoi(value); + } + else if (strcmp(name, "poll_sleep") == 0) + { + gateway.pollsleep = atoi(value); + } + else if (strcmp(name, "ms_timestamp") == 0) + { + skygw_set_highp(config_truth_value((char*)value)); + } else if (strcmp(name, "auth_connect_timeout") == 0) - { + { char* endptr; - int intval = strtol(value, &endptr, 0); - if(*endptr == '\0' && intval > 0) + int intval = strtol(value, &endptr, 0); + if (*endptr == '\0' && intval > 0) + { gateway.auth_conn_timeout = intval; - else - skygw_log_write(LE, "Invalid timeout value for 'auth_connect_timeout': %s", value); - } - else if (strcmp(name, "auth_read_timeout") == 0) - { - char* endptr; - int intval = strtol(value, &endptr, 0); - if(*endptr == '\0' && intval > 0) - gateway.auth_read_timeout = intval; - else - skygw_log_write(LE, "Invalid timeout value for 'auth_read_timeout': %s", value); - } - else if (strcmp(name, "auth_write_timeout") == 0) - { - char* endptr; - int intval = strtol(value, &endptr, 0); - if(*endptr == '\0' && intval > 0) - gateway.auth_write_timeout = intval; - else - skygw_log_write(LE, "Invalid timeout value for 'auth_write_timeout': %s", value); - } - else - { - for (i = 0; lognames[i].logname; i++) - { - if (strcasecmp(name, lognames[i].logname) == 0) - { - if (config_truth_value((char*)value)) - skygw_log_enable(lognames[i].logfile); - else - skygw_log_disable(lognames[i].logfile); - } - } } - return 1; + else + { + skygw_log_write(LE, "Invalid timeout value for 'auth_connect_timeout': %s", value); + } + } + else if (strcmp(name, "auth_read_timeout") == 0) + { + char* endptr; + int intval = strtol(value, &endptr, 0); + if (*endptr == '\0' && intval > 0) + { + gateway.auth_read_timeout = intval; + } + else + { + skygw_log_write(LE, "Invalid timeout value for 'auth_read_timeout': %s", value); + } + } + else if (strcmp(name, "auth_write_timeout") == 0) + { + char* endptr; + int intval = strtol(value, &endptr, 0); + if (*endptr == '\0' && intval > 0) + { + gateway.auth_write_timeout = intval; + } + else + { + skygw_log_write(LE, "Invalid timeout value for 'auth_write_timeout': %s", value); + } + } + else + { + for (i = 0; lognames[i].logname; i++) + { + if (strcasecmp(name, lognames[i].logname) == 0) + { + if (config_truth_value((char*)value)) + { + skygw_log_enable(lognames[i].logfile); + } + else + { + skygw_log_disable(lognames[i].logfile); + } + } + } + } + return 1; } /** * Configuration handler for items in the feedback [feedback] section * - * @param name The item name - * @param value The item value + * @param name The item name + * @param value The item value * @return 0 on error */ -static int +static int handle_feedback_item(const char *name, const char *value) { -int i; - if (strcmp(name, "feedback_enable") == 0) - { - feedback.feedback_enable = config_truth_value((char *)value); - } - else if (strcmp(name, "feedback_user_info") == 0) - { - feedback.feedback_user_info = strdup(value); - } - else if (strcmp(name, "feedback_url") == 0) - { - feedback.feedback_url = strdup(value); - } - if (strcmp(name, "feedback_timeout") == 0) - { - feedback.feedback_timeout = atoi(value); - } - if (strcmp(name, "feedback_connect_timeout") == 0) - { - feedback.feedback_connect_timeout = atoi(value); - } - if (strcmp(name, "feedback_frequency") == 0) - { - feedback.feedback_frequency = atoi(value); - } - return 1; + int i; + if (strcmp(name, "feedback_enable") == 0) + { + feedback.feedback_enable = config_truth_value((char *)value); + } + else if (strcmp(name, "feedback_user_info") == 0) + { + feedback.feedback_user_info = strdup(value); + } + else if (strcmp(name, "feedback_url") == 0) + { + feedback.feedback_url = strdup(value); + } + if (strcmp(name, "feedback_timeout") == 0) + { + feedback.feedback_timeout = atoi(value); + } + if (strcmp(name, "feedback_connect_timeout") == 0) + { + feedback.feedback_connect_timeout = atoi(value); + } + if (strcmp(name, "feedback_frequency") == 0) + { + feedback.feedback_frequency = atoi(value); + } + return 1; } /** @@ -1682,37 +1734,50 @@ int i; static void global_defaults() { - uint8_t mac_addr[6]=""; - struct utsname uname_data; - gateway.n_threads = get_processor_count(); - gateway.n_nbpoll = DEFAULT_NBPOLLS; - gateway.pollsleep = DEFAULT_POLLSLEEP; + uint8_t mac_addr[6]=""; + struct utsname uname_data; + gateway.n_threads = get_processor_count(); + gateway.n_nbpoll = DEFAULT_NBPOLLS; + gateway.pollsleep = DEFAULT_POLLSLEEP; gateway.auth_conn_timeout = DEFAULT_AUTH_CONNECT_TIMEOUT; gateway.auth_read_timeout = DEFAULT_AUTH_READ_TIMEOUT; gateway.auth_write_timeout = DEFAULT_AUTH_WRITE_TIMEOUT; - if (version_string != NULL) - gateway.version_string = strdup(version_string); - else - gateway.version_string = NULL; - gateway.id=0; + if (version_string != NULL) + { + gateway.version_string = strdup(version_string); + } + else + { + gateway.version_string = NULL; + } + gateway.id=0; - /* get release string */ - if(!config_get_release_string(gateway.release_string)) - sprintf(gateway.release_string,"undefined"); + /* get release string */ + if (!config_get_release_string(gateway.release_string)) + { + sprintf(gateway.release_string, "undefined"); + } - /* get first mac_address in SHA1 */ - if(config_get_ifaddr(mac_addr)) { - gw_sha1_str(mac_addr, 6, gateway.mac_sha1); - } else { - memset(gateway.mac_sha1, '\0', sizeof(gateway.mac_sha1)); - memcpy(gateway.mac_sha1, "MAC-undef", 9); - } + /* get first mac_address in SHA1 */ + if (config_get_ifaddr(mac_addr)) + { + gw_sha1_str(mac_addr, 6, gateway.mac_sha1); + } + else + { + memset(gateway.mac_sha1, '\0', sizeof(gateway.mac_sha1)); + memcpy(gateway.mac_sha1, "MAC-undef", 9); + } - /* get uname info */ - if (uname(&uname_data)) - strcpy(gateway.sysname, "undefined"); - else - strncpy(gateway.sysname, uname_data.sysname, _SYSNAME_STR_LENGTH); + /* get uname info */ + if (uname(&uname_data)) + { + strcpy(gateway.sysname, "undefined"); + } + else + { + strncpy(gateway.sysname, uname_data.sysname, _SYSNAME_STR_LENGTH); + } } /** @@ -1721,85 +1786,83 @@ global_defaults() static void feedback_defaults() { - feedback.feedback_enable = 0; - feedback.feedback_user_info = NULL; - feedback.feedback_last_action = _NOTIFICATION_SEND_PENDING; - feedback.feedback_timeout = _NOTIFICATION_OPERATION_TIMEOUT; - feedback.feedback_connect_timeout = _NOTIFICATION_CONNECT_TIMEOUT; - feedback.feedback_url = NULL; - feedback.feedback_frequency = 1800; - feedback.release_info = gateway.release_string; - feedback.sysname = gateway.sysname; - feedback.mac_sha1 = gateway.mac_sha1; + feedback.feedback_enable = 0; + feedback.feedback_user_info = NULL; + feedback.feedback_last_action = _NOTIFICATION_SEND_PENDING; + feedback.feedback_timeout = _NOTIFICATION_OPERATION_TIMEOUT; + feedback.feedback_connect_timeout = _NOTIFICATION_CONNECT_TIMEOUT; + feedback.feedback_url = NULL; + feedback.feedback_frequency = 1800; + feedback.release_info = gateway.release_string; + feedback.sysname = gateway.sysname; + feedback.mac_sha1 = gateway.mac_sha1; } /** * Process a configuration context update and turn it into the set of object * we need. * - * @param context The configuration data + * @param context The configuration data */ -static int +static int process_config_update(CONFIG_CONTEXT *context) { -CONFIG_CONTEXT *obj; -SERVICE *service; -SERVER *server; + CONFIG_CONTEXT *obj; + SERVICE *service; + SERVER *server; - /** - * Process the data and create the services and servers defined - * in the data. - */ - obj = context; - while (obj) - { - char *type = config_get_value(obj->parameters, "type"); - if (type == NULL) + /** + * Process the data and create the services and servers defined + * in the data. + */ + obj = context; + while (obj) + { + char *type = config_get_value(obj->parameters, "type"); + if (type == NULL) + { + LOGIF(LE, + (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Configuration object %s has no type.", + obj->object))); + } + else if (!strcmp(type, "service")) + { + char *router = config_get_value(obj->parameters, + "router"); + if (router) + { + if ((service = service_find(obj->object)) != NULL) { - LOGIF(LE, - (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Configuration object %s has no type.", - obj->object))); - } - else if (!strcmp(type, "service")) - { - char *router = config_get_value(obj->parameters, - "router"); - if (router) - { - if ((service = service_find(obj->object)) != NULL) - { - char *user; - char *auth; - char *enable_root_user; + char *user; + char *auth; + char *enable_root_user; - char *connection_timeout; + char *connection_timeout; - char* auth_all_servers; - char* optimize_wildcard; - char* strip_db_esc; - char* max_slave_conn_str; - char* max_slave_rlag_str; - char *version_string; - char *allow_localhost_match_wildcard_host; + char* auth_all_servers; + char* optimize_wildcard; + char* strip_db_esc; + char* max_slave_conn_str; + char* max_slave_rlag_str; + char *version_string; + char *allow_localhost_match_wildcard_host; - enable_root_user = config_get_value(obj->parameters, "enable_root_user"); + enable_root_user = config_get_value(obj->parameters, "enable_root_user"); - connection_timeout = config_get_value(obj->parameters, "connection_timeout"); - user = config_get_value(obj->parameters, - "user"); - auth = config_get_value(obj->parameters, - "passwd"); - - auth_all_servers = config_get_value(obj->parameters, "auth_all_servers"); - optimize_wildcard = config_get_value(obj->parameters, "optimize_wildcard"); - strip_db_esc = config_get_value(obj->parameters, "strip_db_esc"); - version_string = config_get_value(obj->parameters, "version_string"); - allow_localhost_match_wildcard_host = config_get_value(obj->parameters, "localhost_match_wildcard_host"); + connection_timeout = config_get_value(obj->parameters, "connection_timeout"); + user = config_get_value(obj->parameters, "user"); + auth = config_get_value(obj->parameters, "passwd"); - char *log_auth_warnings = config_get_value(obj->parameters, - "log_auth_warnings"); + auth_all_servers = config_get_value(obj->parameters, "auth_all_servers"); + optimize_wildcard = config_get_value(obj->parameters, "optimize_wildcard"); + strip_db_esc = config_get_value(obj->parameters, "strip_db_esc"); + version_string = config_get_value(obj->parameters, "version_string"); + allow_localhost_match_wildcard_host = + config_get_value(obj->parameters, "localhost_match_wildcard_host"); + + char *log_auth_warnings = config_get_value(obj->parameters, "log_auth_warnings"); int truthval; if (log_auth_warnings && (truthval = config_truth_value(log_auth_warnings)) != -1) { @@ -1808,603 +1871,621 @@ SERVER *server; CONFIG_PARAMETER* param; - if((param = config_get_param(obj->parameters, "ignore_databases"))) + if ((param = config_get_param(obj->parameters, "ignore_databases"))) { service_set_param_value(service, param, param->value, 0, STRING_TYPE); } - if((param = config_get_param(obj->parameters, "ignore_databases_regex"))) + if ((param = config_get_param(obj->parameters, "ignore_databases_regex"))) { service_set_param_value(service, param, param->value, 0, STRING_TYPE); } - if (version_string) { - if (service->version_string) { - free(service->version_string); - } - service->version_string = strdup(version_string); - } + if (version_string) + { + if (service->version_string) + { + free(service->version_string); + } + service->version_string = strdup(version_string); + } - if (user && auth) { - service_update(service, router, - user, - auth); - if (enable_root_user) - serviceEnableRootUser(service, config_truth_value(enable_root_user)); + if (user && auth) + { + service_update(service, router, user, auth); + if (enable_root_user) + { + serviceEnableRootUser(service, config_truth_value(enable_root_user)); + } - if (connection_timeout) - serviceSetTimeout(service, config_truth_value(connection_timeout)); + if (connection_timeout) + { + serviceSetTimeout(service, config_truth_value(connection_timeout)); + } + if (auth_all_servers) + { + serviceAuthAllServers(service, config_truth_value(auth_all_servers)); + } + if (optimize_wildcard) + { + serviceOptimizeWildcard(service, config_truth_value(optimize_wildcard)); + } - if(auth_all_servers) - serviceAuthAllServers(service, config_truth_value(auth_all_servers)); - if(optimize_wildcard) - serviceOptimizeWildcard(service, config_truth_value(optimize_wildcard)); - if(strip_db_esc) - serviceStripDbEsc(service, config_truth_value(strip_db_esc)); + if (strip_db_esc) + { + serviceStripDbEsc(service, config_truth_value(strip_db_esc)); + } - if (allow_localhost_match_wildcard_host) - serviceEnableLocalhostMatchWildcardHost( - service, - config_truth_value(allow_localhost_match_wildcard_host)); - - /** Read, validate and set max_slave_connections */ - max_slave_conn_str = - config_get_value( - obj->parameters, - "max_slave_connections"); + if (allow_localhost_match_wildcard_host) + serviceEnableLocalhostMatchWildcardHost( + service, + config_truth_value(allow_localhost_match_wildcard_host)); - if (max_slave_conn_str != NULL) - { - CONFIG_PARAMETER* param; - bool succp; - - param = config_get_param(obj->parameters, - "max_slave_connections"); - - if (param == NULL) - { - succp = false; - } - else - { - succp = service_set_param_value( - service, - param, - max_slave_conn_str, - COUNT_ATMOST, - (PERCENT_TYPE|COUNT_TYPE)); - } - - if (!succp && param != NULL) - { - LOGIF(LM, (skygw_log_write( - LOGFILE_MESSAGE, - "* Warning : invalid value type " - "for parameter \'%s.%s = %s\'\n\tExpected " - "type is either for slave connection " - "count or\n\t%% for specifying the " - "maximum percentage of available the " - "slaves that will be connected.", - ((SERVICE*)obj->element)->name, - param->name, - param->value))); - } - } - /** Read, validate and set max_slave_replication_lag */ - max_slave_rlag_str = - config_get_value(obj->parameters, - "max_slave_replication_lag"); - - if (max_slave_rlag_str != NULL) - { - CONFIG_PARAMETER* param; - bool succp; - - param = config_get_param( - obj->parameters, - "max_slave_replication_lag"); - - if (param == NULL) - { - succp = false; - } - else - { - succp = service_set_param_value( - service, - param, - max_slave_rlag_str, - COUNT_ATMOST, - COUNT_TYPE); - } - - if (!succp) - { - if(param){ - LOGIF(LM, (skygw_log_write( - LOGFILE_MESSAGE, - "* Warning : invalid value type " - "for parameter \'%s.%s = %s\'\n\tExpected " - "type is for maximum " - "slave replication lag.", - ((SERVICE*)obj->element)->name, - param->name, - param->value))); - }else{ - LOGIF(LE, (skygw_log_write( - LOGFILE_ERROR, - "Error : parameter was NULL"))); - } - } - } - } + /** Read, validate and set max_slave_connections */ + max_slave_conn_str = + config_get_value(obj->parameters, "max_slave_connections"); - obj->element = service; - } - else - { + if (max_slave_conn_str != NULL) + { + CONFIG_PARAMETER* param; + bool succp; + + param = config_get_param(obj->parameters, + "max_slave_connections"); + + if (param == NULL) + { + succp = false; + } + else + { + succp = service_set_param_value( + service, + param, + max_slave_conn_str, + COUNT_ATMOST, + (PERCENT_TYPE|COUNT_TYPE)); + } + + if (!succp && param != NULL) + { + LOGIF(LM, (skygw_log_write( + LOGFILE_MESSAGE, + "* Warning : invalid value type " + "for parameter \'%s.%s = %s\'\n\tExpected " + "type is either for slave connection " + "count or\n\t%% for specifying the " + "maximum percentage of available the " + "slaves that will be connected.", + ((SERVICE*)obj->element)->name, + param->name, + param->value))); + } + } + /** Read, validate and set max_slave_replication_lag */ + max_slave_rlag_str = + config_get_value(obj->parameters, "max_slave_replication_lag"); + + if (max_slave_rlag_str != NULL) + { + CONFIG_PARAMETER* param; + bool succp; + + param = config_get_param(obj->parameters, + "max_slave_replication_lag"); + + if (param == NULL) + { + succp = false; + } + else + { + succp = service_set_param_value(service, + param, + max_slave_rlag_str, + COUNT_ATMOST, + COUNT_TYPE); + } + + if (!succp) + { + if(param){ + LOGIF(LM, (skygw_log_write( + LOGFILE_MESSAGE, + "* Warning : invalid value type " + "for parameter \'%s.%s = %s\'\n\tExpected " + "type is for maximum " + "slave replication lag.", + ((SERVICE*)obj->element)->name, + param->name, + param->value))); + } + else + { + LOGIF(LE, (skygw_log_write( + LOGFILE_ERROR, + "Error : parameter was NULL"))); + } + } + } + } + + obj->element = service; + } + else + { char *user; - char *auth; - char *enable_root_user; - char *connection_timeout; - char *allow_localhost_match_wildcard_host; + char *auth; + char *enable_root_user; + char *connection_timeout; + char *allow_localhost_match_wildcard_host; - enable_root_user = - config_get_value(obj->parameters, - "enable_root_user"); + enable_root_user = config_get_value(obj->parameters, + "enable_root_user"); - connection_timeout = config_get_value(obj->parameters, + connection_timeout = config_get_value(obj->parameters, "connection_timeout"); - allow_localhost_match_wildcard_host = - config_get_value(obj->parameters, "localhost_match_wildcard_host"); - - user = config_get_value(obj->parameters, - "user"); - auth = config_get_value(obj->parameters, - "passwd"); - obj->element = service_alloc(obj->object, - router); - - if (obj->element && user && auth) - { - serviceSetUser(obj->element, - user, - auth); - if (enable_root_user) - serviceEnableRootUser(obj->element, config_truth_value(enable_root_user)); + allow_localhost_match_wildcard_host = + config_get_value(obj->parameters, "localhost_match_wildcard_host"); - if (connection_timeout) - serviceSetTimeout(obj->element, atoi(connection_timeout)); + user = config_get_value(obj->parameters, "user"); + auth = config_get_value(obj->parameters, "passwd"); + obj->element = service_alloc(obj->object, router); - if (allow_localhost_match_wildcard_host) - serviceEnableLocalhostMatchWildcardHost( - obj->element, - config_truth_value(allow_localhost_match_wildcard_host)); - } - } - } - else - { - obj->element = NULL; - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : No router defined for service " - "'%s'.", - obj->object))); - } - } - else if (!strcmp(type, "server")) - { - char *address; - char *port; - char *protocol; - char *monuser; - char *monpw; - - address = config_get_value(obj->parameters, "address"); - port = config_get_value(obj->parameters, "port"); - protocol = config_get_value(obj->parameters, "protocol"); - monuser = config_get_value(obj->parameters, - "monitoruser"); - monpw = config_get_value(obj->parameters, "monitorpw"); - - if (address && port && protocol) - { - if ((server = - server_find(address, atoi(port))) != NULL) - { - server_update(server, - protocol, - monuser, - monpw); - obj->element = server; - } - else - { - obj->element = server_alloc(address, - protocol, - atoi(port)); - - server_set_unique_name(obj->element, obj->object); - - if (obj->element && monuser && monpw) - { - serverAddMonUser(obj->element, - monuser, - monpw); - } - } - } - else + if (obj->element && user && auth) + { + serviceSetUser(obj->element, + user, + auth); + if (enable_root_user) { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Server '%s' is missing a " - "required " - "configuration parameter. A server must " - "have address, port and protocol " - "defined.", - obj->object))); + serviceEnableRootUser(obj->element, config_truth_value(enable_root_user)); } - } - obj = obj->next; - } - /* - * Now we have the services we can add the servers to the services - * add the protocols to the services - */ - obj = context; - while (obj) - { - char *type = config_get_value(obj->parameters, "type"); - if (type == NULL) - ; - else if (!strcmp(type, "service")) - { - char *servers; - char *roptions; - char *filters; - - servers = config_get_value(obj->parameters, "servers"); - roptions = config_get_value(obj->parameters, - "router_options"); - filters = config_get_value(obj->parameters, "filters"); - if (servers && obj->element) - { - char *lasts; - char *s = strtok_r(servers, ",", &lasts); - while (s) - { - CONFIG_CONTEXT *obj1 = context; - int found = 0; - while (obj1) - { - if (strcmp(trim(s), obj1->object) == 0 && - obj->element && obj1->element) - { - found = 1; - if (!serviceHasBackend(obj->element, obj1->element)) - { - serviceAddBackend( - obj->element, - obj1->element); - } - } - obj1 = obj1->next; - } - if (!found) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error: Unable to find " - "server '%s' that is " - "configured as part of " - "service '%s'.", - s, obj->object))); - } - s = strtok_r(NULL, ",", &lasts); - } - } - if (roptions && obj->element) - { - char *lasts; - char *s = strtok_r(roptions, ",", &lasts); - serviceClearRouterOptions(obj->element); - while (s) - { - serviceAddRouterOption(obj->element, s); - s = strtok_r(NULL, ",", &lasts); - } - } - if (filters && obj->element) - serviceSetFilters(obj->element, filters); - } - else if (!strcmp(type, "listener")) - { - char *service; - char *port; - char *protocol; - char *address; - char *socket; + if (connection_timeout) + { + serviceSetTimeout(obj->element, atoi(connection_timeout)); + } - service = config_get_value(obj->parameters, "service"); - address = config_get_value(obj->parameters, "address"); - port = config_get_value(obj->parameters, "port"); - protocol = config_get_value(obj->parameters, "protocol"); - socket = config_get_value(obj->parameters, "socket"); + if (allow_localhost_match_wildcard_host) + { + serviceEnableLocalhostMatchWildcardHost( + obj->element, + config_truth_value(allow_localhost_match_wildcard_host)); + } + } + } + } + else + { + obj->element = NULL; + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : No router defined for service " + "'%s'.", + obj->object))); + } + } + else if (!strcmp(type, "server")) + { + char *address; + char *port; + char *protocol; + char *monuser; + char *monpw; - if (service && socket && protocol) - { - CONFIG_CONTEXT *ptr = context; - while (ptr && strcmp(ptr->object, service) != 0) - ptr = ptr->next; - - if (ptr && - ptr->element && - serviceHasProtocol(ptr->element, - protocol, - 0) == 0) - { - serviceAddProtocol(ptr->element, - protocol, - socket, - 0); - serviceStartProtocol(ptr->element, - protocol, - 0); - } - } + address = config_get_value(obj->parameters, "address"); + port = config_get_value(obj->parameters, "port"); + protocol = config_get_value(obj->parameters, "protocol"); + monuser = config_get_value(obj->parameters, "monitoruser"); + monpw = config_get_value(obj->parameters, "monitorpw"); - if (service && port && protocol) - { - CONFIG_CONTEXT *ptr = context; - while (ptr && strcmp(ptr->object, service) != 0) - ptr = ptr->next; - - if (ptr && - ptr->element && - serviceHasProtocol(ptr->element, - protocol, - atoi(port)) == 0) - { - serviceAddProtocol(ptr->element, - protocol, - address, - atoi(port)); - serviceStartProtocol(ptr->element, - protocol, - atoi(port)); - } - } - } - else if (strcmp(type, "server") != 0 && - strcmp(type, "monitor") != 0 && - strcmp(type, "filter") != 0) - { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Configuration object %s has an invalid " - "type specified.", - obj->object))); - } - obj = obj->next; - } - return 1; + if (address && port && protocol) + { + if ((server = server_find(address, atoi(port))) != NULL) + { + server_update(server, + protocol, + monuser, + monpw); + obj->element = server; + } + else + { + obj->element = server_alloc(address, + protocol, + atoi(port)); + + server_set_unique_name(obj->element, obj->object); + + if (obj->element && monuser && monpw) + { + serverAddMonUser(obj->element, + monuser, + monpw); + } + } + } + else + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Server '%s' is missing a " + "required " + "configuration parameter. A server must " + "have address, port and protocol " + "defined.", + obj->object))); + } + } + obj = obj->next; + } + + /* + * Now we have the services we can add the servers to the services + * add the protocols to the services + */ + obj = context; + while (obj) + { + char *type = config_get_value(obj->parameters, "type"); + if (type == NULL) + { + ; + } + else if (!strcmp(type, "service")) + { + char *servers; + char *roptions; + char *filters; + + servers = config_get_value(obj->parameters, "servers"); + roptions = config_get_value(obj->parameters, "router_options"); + filters = config_get_value(obj->parameters, "filters"); + + if (servers && obj->element) + { + char *lasts; + char *s = strtok_r(servers, ",", &lasts); + while (s) + { + CONFIG_CONTEXT *obj1 = context; + int found = 0; + while (obj1) + { + if (strcmp(trim(s), obj1->object) == 0 && obj->element && obj1->element) + { + found = 1; + if (!serviceHasBackend(obj->element, obj1->element)) + { + serviceAddBackend(obj->element, obj1->element); + } + } + + obj1 = obj1->next; + } + if (!found) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error: Unable to find " + "server '%s' that is " + "configured as part of " + "service '%s'.", + s, obj->object))); + } + s = strtok_r(NULL, ",", &lasts); + } + } + if (roptions && obj->element) + { + char *lasts; + char *s = strtok_r(roptions, ",", &lasts); + serviceClearRouterOptions(obj->element); + while (s) + { + serviceAddRouterOption(obj->element, s); + s = strtok_r(NULL, ",", &lasts); + } + } + if (filters && obj->element) + { + serviceSetFilters(obj->element, filters); + } + } + else if (!strcmp(type, "listener")) + { + char *service; + char *port; + char *protocol; + char *address; + char *socket; + + service = config_get_value(obj->parameters, "service"); + address = config_get_value(obj->parameters, "address"); + port = config_get_value(obj->parameters, "port"); + protocol = config_get_value(obj->parameters, "protocol"); + socket = config_get_value(obj->parameters, "socket"); + + if (service && socket && protocol) + { + CONFIG_CONTEXT *ptr = context; + while (ptr && strcmp(ptr->object, service) != 0) + { + ptr = ptr->next; + } + + if (ptr && + ptr->element && + serviceHasProtocol(ptr->element, protocol, 0) == 0) + { + serviceAddProtocol(ptr->element, protocol, socket, 0); + serviceStartProtocol(ptr->element, protocol, 0); + } + } + + if (service && port && protocol) + { + CONFIG_CONTEXT *ptr = context; + + while (ptr && strcmp(ptr->object, service) != 0) + { + ptr = ptr->next; + } + + if (ptr && + ptr->element && + serviceHasProtocol(ptr->element, protocol, atoi(port)) == 0) + { + serviceAddProtocol(ptr->element, protocol, address, atoi(port)); + serviceStartProtocol(ptr->element, protocol, atoi(port)); + } + } + } + else if (strcmp(type, "server") != 0 && + strcmp(type, "monitor") != 0 && + strcmp(type, "filter") != 0) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Configuration object %s has an invalid " + "type specified.", + obj->object))); + } + obj = obj->next; + } + + return 1; } static char *service_params[] = - { - "type", - "router", - "router_options", - "servers", - "user", - "passwd", - "enable_root_user", - "connection_timeout", - "auth_all_servers", - "optimize_wildcard", - "strip_db_esc", - "localhost_match_wildcard_host", - "max_slave_connections", - "max_slave_replication_lag", - "use_sql_variables_in", /*< rwsplit only */ - "subservices", - "version_string", - "filters", - "weightby", - "ssl_cert", - "ssl_ca_cert", - "ssl", - "ssl_key", - "ssl_version", - "ssl_cert_verify_depth", - "ignore_databases", - "ignore_databases_regex", - "log_auth_warnings", - NULL - }; +{ + "type", + "router", + "router_options", + "servers", + "user", + "passwd", + "enable_root_user", + "connection_timeout", + "auth_all_servers", + "optimize_wildcard", + "strip_db_esc", + "localhost_match_wildcard_host", + "max_slave_connections", + "max_slave_replication_lag", + "use_sql_variables_in", /*< rwsplit only */ + "subservices", + "version_string", + "filters", + "weightby", + "ssl_cert", + "ssl_ca_cert", + "ssl", + "ssl_key", + "ssl_version", + "ssl_cert_verify_depth", + "ignore_databases", + "ignore_databases_regex", + "log_auth_warnings", + NULL +}; static char *listener_params[] = - { - "type", - "service", - "protocol", - "port", - "address", - "socket", - NULL - }; +{ + "type", + "service", + "protocol", + "port", + "address", + "socket", + NULL +}; static char *monitor_params[] = - { - "type", - "module", - "servers", - "user", - "passwd", - "script", - "events", - "mysql51_replication", - "monitor_interval", - "detect_replication_lag", - "detect_stale_master", - "disable_master_failback", - "backend_connect_timeout", - "backend_read_timeout", - "backend_write_timeout", - "available_when_donor", - "disable_master_role_setting", - NULL - }; +{ + "type", + "module", + "servers", + "user", + "passwd", + "script", + "events", + "mysql51_replication", + "monitor_interval", + "detect_replication_lag", + "detect_stale_master", + "disable_master_failback", + "backend_connect_timeout", + "backend_read_timeout", + "backend_write_timeout", + "available_when_donor", + "disable_master_role_setting", + NULL +}; /** * Check the configuration objects have valid parameters */ static void check_config_objects(CONFIG_CONTEXT *context) { -CONFIG_CONTEXT *obj; -CONFIG_PARAMETER *params; -char *type, **param_set; -int i; + CONFIG_CONTEXT *obj; + CONFIG_PARAMETER *params; + char *type, **param_set; + int i; - /** - * Process the data and create the services and servers defined - * in the data. - */ - obj = context; - while (obj) - { - param_set = NULL; - if (obj->parameters && - (type = config_get_value(obj->parameters, "type"))) - { - if (!strcmp(type, "service")) - param_set = service_params; - else if (!strcmp(type, "listener")) - param_set = listener_params; - else if (!strcmp(type, "monitor")) - param_set = monitor_params; - } - if (param_set != NULL) - { - params = obj->parameters; - while (params) - { - int found = 0; - for (i = 0; param_set[i]; i++) - if (!strcmp(params->name, param_set[i])) - found = 1; - if (found == 0) - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error : Unexpected parameter " - "'%s' for object '%s' of type " - "'%s'.", - params->name, - obj->object, - type))); - params = params->next; - } - } - obj = obj->next; - } + /** + * Process the data and create the services and servers defined + * in the data. + */ + obj = context; + while (obj) + { + param_set = NULL; + if (obj->parameters && (type = config_get_value(obj->parameters, "type"))) + { + if (!strcmp(type, "service")) + { + param_set = service_params; + } + else if (!strcmp(type, "listener")) + { + param_set = listener_params; + } + else if (!strcmp(type, "monitor")) + { + param_set = monitor_params; + } + } + + if (param_set != NULL) + { + params = obj->parameters; + while (params) + { + int found = 0; + for (i = 0; param_set[i]; i++) + { + if (!strcmp(params->name, param_set[i])) + { + found = 1; + } + } + + if (found == 0) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error : Unexpected parameter " + "'%s' for object '%s' of type " + "'%s'.", + params->name, + obj->object, + type))); + } + params = params->next; + } + } + obj = obj->next; + } } /** * Set qualified parameter value to CONFIG_PARAMETER struct. */ -bool config_set_qualified_param( - CONFIG_PARAMETER* param, - void* val, - config_param_type_t type) +bool config_set_qualified_param(CONFIG_PARAMETER* param, + void* val, + config_param_type_t type) { - bool succp; - - switch (type) { - case STRING_TYPE: - param->qfd.valstr = strndup((const char *)val, MAX_PARAM_LEN); - succp = true; - break; + bool succp; - case COUNT_TYPE: - param->qfd.valcount = *(int *)val; - succp = true; - break; - - case PERCENT_TYPE: - param->qfd.valpercent = *(int *)val; - succp = true; - break; - - case BOOL_TYPE: - param->qfd.valbool = *(bool *)val; - succp = true; - break; + switch (type) + { + case STRING_TYPE: + param->qfd.valstr = strndup((const char *)val, MAX_PARAM_LEN); + succp = true; + break; - case SQLVAR_TARGET_TYPE: - param->qfd.valtarget = *(target_t *)val; - succp = true; - break; - default: - succp = false; - break; - } - - if (succp) - { - param->qfd_param_type = type; - } - return succp; + case COUNT_TYPE: + param->qfd.valcount = *(int *)val; + succp = true; + break; + + case PERCENT_TYPE: + param->qfd.valpercent = *(int *)val; + succp = true; + break; + + case BOOL_TYPE: + param->qfd.valbool = *(bool *)val; + succp = true; + break; + + case SQLVAR_TARGET_TYPE: + param->qfd.valtarget = *(target_t *)val; + succp = true; + break; + default: + succp = false; + break; + } + + if (succp) + { + param->qfd_param_type = type; + } + return succp; } /** * Used for boolean settings where values may be 1, yes or true * to enable a setting or -, no, false to disable a setting. * - * @param str String to convert to a boolean - * @return Truth value + * @param str String to convert to a boolean + * @return Truth value */ int config_truth_value(char *str) { - if (strcasecmp(str, "true") == 0 || strcasecmp(str, "on") == 0 || - strcasecmp(str, "yes") == 0 || strcasecmp(str, "1") == 0) - { - return 1; - } - if (strcasecmp(str, "false") == 0 || strcasecmp(str, "off") == 0 || - strcasecmp(str, "no") == 0|| strcasecmp(str, "0") == 0) - { - return 0; - } - skygw_log_write(LOGFILE_ERROR,"Error: Not a boolean value: %s",str); - return -1; + if (strcasecmp(str, "true") == 0 || strcasecmp(str, "on") == 0 || + strcasecmp(str, "yes") == 0 || strcasecmp(str, "1") == 0) + { + return 1; + } + if (strcasecmp(str, "false") == 0 || strcasecmp(str, "off") == 0 || + strcasecmp(str, "no") == 0|| strcasecmp(str, "0") == 0) + { + return 0; + } + skygw_log_write(LOGFILE_ERROR, "Error: Not a boolean value: %s", str); + return -1; } /** * Converts a string into a floating point representation of a percentage value. * For example 75% is converted to 0.75 and -10% is converted to -0.1. - * @param str String to convert - * @return String converted to a floating point percentage + * @param str String to convert + * @return String converted to a floating point percentage */ double config_percentage_value(char *str) { double value = 0; - value = strtod(str,NULL); - if(value != 0) - value /= 100.0; + value = strtod(str, NULL); + if (value != 0) + { + value /= 100.0; + } return value; } -static char *InternalRouters[] = { +static char *InternalRouters[] = +{ "debugcli", "cli", "maxinfo", @@ -2417,251 +2498,292 @@ static char *InternalRouters[] = { * Determine if the router is one of the special internal services that * MaxScale offers. * - * @param router The router name - * @return Non-zero if the router is in the InternalRouters table + * @param router The router name + * @return Non-zero if the router is in the InternalRouters table */ bool isInternalService(char *router) { - if (router) - { - for (int i = 0; InternalRouters[i]; i++) - if (strcmp(router, InternalRouters[i]) == 0) - return true; - } - return false; + if (router) + { + for (int i = 0; InternalRouters[i]; i++) + { + if (strcmp(router, InternalRouters[i]) == 0) + { + return true; + } + } + } + return false; } /** * Get the MAC address of first network interface * * and fill the provided allocated buffer with SHA1 encoding - * @param output Allocated 6 bytes buffer + * @param output Allocated 6 bytes buffer * @return 1 on success, 0 on failure * */ int config_get_ifaddr(unsigned char *output) { - struct ifreq ifr; - struct ifconf ifc; - char buf[1024]; - struct ifreq* it; - struct ifreq* end; - int success = 0; + struct ifreq ifr; + struct ifconf ifc; + char buf[1024]; + struct ifreq* it; + struct ifreq* end; + int success = 0; - int sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); - if (sock == -1) { - return 0; - }; + int sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); + if (sock == -1) + { + return 0; + } - ifc.ifc_len = sizeof(buf); - ifc.ifc_buf = buf; - if (ioctl(sock, SIOCGIFCONF, &ifc) == -1) { - close(sock); - return 0; - } + ifc.ifc_len = sizeof(buf); + ifc.ifc_buf = buf; + if (ioctl(sock, SIOCGIFCONF, &ifc) == -1) + { + close(sock); + return 0; + } - it = ifc.ifc_req; - end = it + (ifc.ifc_len / sizeof(struct ifreq)); + it = ifc.ifc_req; + end = it + (ifc.ifc_len / sizeof(struct ifreq)); - for (; it != end; ++it) { - strcpy(ifr.ifr_name, it->ifr_name); - if (ioctl(sock, SIOCGIFFLAGS, &ifr) == 0) { - if (! (ifr.ifr_flags & IFF_LOOPBACK)) { /* don't count loopback */ - if (ioctl(sock, SIOCGIFHWADDR, &ifr) == 0) { - success = 1; - break; - } - } - } else { - close(sock); - return 0; - } - } + for (; it != end; ++it) + { + strcpy(ifr.ifr_name, it->ifr_name); - if (success) - memcpy(output, ifr.ifr_hwaddr.sa_data, 6); + if (ioctl(sock, SIOCGIFFLAGS, &ifr) == 0) + { + if (!(ifr.ifr_flags & IFF_LOOPBACK)) + { /* don't count loopback */ + if (ioctl(sock, SIOCGIFHWADDR, &ifr) == 0) + { + success = 1; + break; + } + } + } + else + { + close(sock); + return 0; + } + } - return success; + if (success) + { + memcpy(output, ifr.ifr_hwaddr.sa_data, 6); + } + + return success; } /** * Get the linux distribution info * - * @param release The allocated buffer where - * the found distribution is copied into. + * @param release The allocated buffer where + * the found distribution is copied into. * @return 1 on success, 0 on failure * */ int config_get_release_string(char* release) { - const char *masks[]= { - "/etc/*-version", "/etc/*-release", - "/etc/*_version", "/etc/*_release" - }; + const char *masks[] = + { + "/etc/*-version", "/etc/*-release", + "/etc/*_version", "/etc/*_release" + }; - bool have_distribution; - char distribution[_RELEASE_STR_LENGTH]=""; - int fd; - int i; - char *to; + bool have_distribution; + char distribution[_RELEASE_STR_LENGTH]=""; + int fd; + int i; + char *to; - have_distribution= false; + have_distribution= false; - /* get data from lsb-release first */ - if ((fd= open("/etc/lsb-release", O_RDONLY)) != -1) - { - /* LSB-compliant distribution! */ - size_t len= read(fd, (char*)distribution, sizeof(distribution)-1); - close(fd); - if (len != (size_t)-1) - { - distribution[len]= 0; - char *found= strstr(distribution, "DISTRIB_DESCRIPTION="); - if (found) - { - have_distribution = true; - char *end = strstr(found, "\n"); - if (end == NULL) - end = distribution + len; - found += 20; + /* get data from lsb-release first */ + if ((fd = open("/etc/lsb-release", O_RDONLY)) != -1) + { + /* LSB-compliant distribution! */ + size_t len = read(fd, (char*)distribution, sizeof(distribution) - 1); + close(fd); - if (*found == '"' && end[-1] == '"') - { - found++; - end--; - } - *end = 0; + if (len != (size_t)-1) + { + distribution[len]= 0; - to = strcpy(distribution, "lsb: "); - memmove(to, found, end - found + 1 < INT_MAX ? end - found + 1 : INT_MAX); + char *found= strstr(distribution, "DISTRIB_DESCRIPTION="); - strncpy(release, to, _RELEASE_STR_LENGTH); + if (found) + { + have_distribution = true; + char *end = strstr(found, "\n"); + if (end == NULL) + { + end = distribution + len; + } + found += 20; - return 1; - } - } - } + if (*found == '"' && end[-1] == '"') + { + found++; + end--; + } + *end = 0; - /* if not an LSB-compliant distribution */ - for (i= 0; !have_distribution && i < 4; i++) - { - glob_t found; - char *new_to; + to = strcpy(distribution, "lsb: "); + memmove(to, found, end - found + 1 < INT_MAX ? end - found + 1 : INT_MAX); - if (glob(masks[i], GLOB_NOSORT, NULL, &found) == 0) - { - int fd; - int k = 0; - int skipindex = 0; - int startindex = 0; + strncpy(release, to, _RELEASE_STR_LENGTH); - for (k = 0; k< found.gl_pathc; k++) { - if (strcmp(found.gl_pathv[k], "/etc/lsb-release") == 0) { - skipindex = k; - } - } + return 1; + } + } + } - if ( skipindex == 0) - startindex++; + /* if not an LSB-compliant distribution */ + for (i = 0; !have_distribution && i < 4; i++) + { + glob_t found; + char *new_to; - if ((fd= open(found.gl_pathv[startindex], O_RDONLY)) != -1) - { - /* - +5 and -8 below cut the file name part out of the - full pathname that corresponds to the mask as above. - */ - new_to = strncpy(distribution, found.gl_pathv[0] + 5,_RELEASE_STR_LENGTH - 1); - new_to += 8; - *new_to++ = ':'; - *new_to++ = ' '; + if (glob(masks[i], GLOB_NOSORT, NULL, &found) == 0) + { + int fd; + int k = 0; + int skipindex = 0; + int startindex = 0; - size_t to_len= distribution + sizeof(distribution) - 1 - new_to; - size_t len= read(fd, (char*)new_to, to_len); + for (k = 0; k< found.gl_pathc; k++) + { + if (strcmp(found.gl_pathv[k], "/etc/lsb-release") == 0) + { + skipindex = k; + } + } - close(fd); + if (skipindex == 0) + startindex++; - if (len != (size_t)-1) - { - new_to[len]= 0; - char *end= strstr(new_to, "\n"); - if (end) - *end= 0; + if ((fd = open(found.gl_pathv[startindex], O_RDONLY)) != -1) + { + /* + +5 and -8 below cut the file name part out of the + full pathname that corresponds to the mask as above. + */ + new_to = strncpy(distribution, found.gl_pathv[0] + 5, _RELEASE_STR_LENGTH - 1); + new_to += 8; + *new_to++ = ':'; + *new_to++ = ' '; - have_distribution= true; - strncpy(release, new_to, _RELEASE_STR_LENGTH); - } - } - } - globfree(&found); - } + size_t to_len = distribution + sizeof(distribution) - 1 - new_to; + size_t len = read(fd, (char*)new_to, to_len); - if (have_distribution) - return 1; - else - return 0; + close(fd); + + if (len != (size_t)-1) + { + new_to[len]= 0; + char *end= strstr(new_to, "\n"); + if (end) + { + *end= 0; + } + + have_distribution= true; + strncpy(release, new_to, _RELEASE_STR_LENGTH); + } + } + } + globfree(&found); + } + + if (have_distribution) + { + return 1; + } + else + { + return 0; + } } /** * Add the 'send_feedback' task to the task list */ void -config_enable_feedback_task(void) { - FEEDBACK_CONF *cfg = config_get_feedback_data(); - int url_set = 0; - int user_info_set = 0; - int enable_set = cfg->feedback_enable; +config_enable_feedback_task(void) +{ + FEEDBACK_CONF *cfg = config_get_feedback_data(); + int url_set = 0; + int user_info_set = 0; + int enable_set = cfg->feedback_enable; - url_set = cfg->feedback_url != NULL && strlen(cfg->feedback_url); - user_info_set = cfg->feedback_user_info != NULL && strlen(cfg->feedback_user_info); + url_set = cfg->feedback_url != NULL && strlen(cfg->feedback_url); + user_info_set = cfg->feedback_user_info != NULL && strlen(cfg->feedback_user_info); - if (enable_set && url_set && user_info_set) { - /* Add the task to the tasl list */ - if (hktask_add("send_feedback", module_feedback_send, cfg, cfg->feedback_frequency)) { - - LOGIF(LM, (skygw_log_write_flush( - LOGFILE_MESSAGE, - "Notification service feedback task started: URL=%s, User-Info=%s, Frequency %u seconds", - cfg->feedback_url, - cfg->feedback_user_info, - cfg->feedback_frequency))); - } - } else { - if (enable_set) { - LOGIF(LE, (skygw_log_write_flush( - LOGFILE_ERROR, - "Error: Notification service feedback cannot start: feedback_enable=1 but" - " some required parameters are not set: %s%s%s", - url_set == 0 ? "feedback_url is not set" : "", (user_info_set == 0 && url_set == 0) ? ", " : "", user_info_set == 0 ? "feedback_user_info is not set" : ""))); - } else { - LOGIF(LT, (skygw_log_write_flush( - LOGFILE_TRACE, - "Notification service feedback is not enabled"))); - } - } + if (enable_set && url_set && user_info_set) + { + /* Add the task to the tasl list */ + if (hktask_add("send_feedback", module_feedback_send, cfg, cfg->feedback_frequency)) + { + LOGIF(LM, (skygw_log_write_flush( + LOGFILE_MESSAGE, + "Notification service feedback task started: URL=%s, User-Info=%s, " + "Frequency %u seconds", + cfg->feedback_url, + cfg->feedback_user_info, + cfg->feedback_frequency))); + } + } + else + { + if (enable_set) + { + LOGIF(LE, (skygw_log_write_flush( + LOGFILE_ERROR, + "Error: Notification service feedback cannot start: feedback_enable=1 but" + " some required parameters are not set: %s%s%s", + url_set == 0 ? "feedback_url is not set" : "", + (user_info_set == 0 && url_set == 0) ? ", " : "", + user_info_set == 0 ? "feedback_user_info is not set" : ""))); + } + else + { + LOGIF(LT, (skygw_log_write_flush( + LOGFILE_TRACE, + "Notification service feedback is not enabled"))); + } + } } /** * Remove the 'send_feedback' task */ void -config_disable_feedback_task(void) { - hktask_remove("send_feedback"); +config_disable_feedback_task(void) +{ + hktask_remove("send_feedback"); } -unsigned long config_get_gateway_id() +unsigned long config_get_gateway_id() { return gateway.id; } -void config_add_param(CONFIG_CONTEXT* obj, char* key,char* value) + +void config_add_param(CONFIG_CONTEXT* obj, char* key, char* value) { CONFIG_PARAMETER* nptr = malloc(sizeof(CONFIG_PARAMETER)); - if(nptr == NULL) + if (nptr == NULL) { - skygw_log_write(LOGFILE_ERROR,"Memory allocation failed when adding configuration parameters"); - return; + skygw_log_write(LOGFILE_ERROR, "Memory allocation failed when adding configuration parameters"); + return; } nptr->name = strdup(key); @@ -2697,8 +2819,7 @@ bool config_has_duplicate_sections(const char* config) int size = 1024; char *buffer = malloc(size * sizeof(char)); - if (buffer && hash && re && - (mdata = pcre2_match_data_create_from_pattern(re, NULL))) + if (buffer && hash && re && (mdata = pcre2_match_data_create_from_pattern(re, NULL))) { hashtable_memory_fns(hash, (HASHMEMORYFN) strdup, NULL, (HASHMEMORYFN) free, NULL);