<p>Sean Bright has uploaded this change for <strong>review</strong>.</p><p><a href="https://gerrit.asterisk.org/7756">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">cdr_mysql: Make sure connection charset is always set<br><br>When the MYSQL_OPT_RECONNECT option is enabled, the MySQL client API<br>will transparently reconnect when it needs to. Ideally this simplifies<br>our code, but when this reconnection occurs all connection state is<br>lost. Because we are not notified that this has happened, we don't know<br>to set our character set again (with "SET NAMES 'xyz'").<br><br>Rather than calling SET NAMES, we instead set the MYSQL_SET_CHARSET_NAME<br>option which will do it for us under the hood on each connect. This<br>option has been present in the MySQL C API for at least 15 years, so it<br>should be safe for most installations.<br><br>I also snuck a few other changes into this patch:<br><br>* Default the MySQL port to MYSQL_PORT (3306) instead of 0 if it's not<br> defined.<br><br>* Fix some erroneous and/or silly checks on the contents of the<br> configuration ast_str values.<br><br>ASTERISK-27366 #close<br>Reported by: Halil İbrahim YILDIZ<br><br>Change-Id: I36bf8dc5d5f83584e803b3b1a151dea9396ab8f5<br>---<br>M addons/cdr_mysql.c<br>1 file changed, 21 insertions(+), 14 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://gerrit.asterisk.org:29418/asterisk refs/changes/56/7756/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">diff --git a/addons/cdr_mysql.c b/addons/cdr_mysql.c<br>index c5cf108..53ea923 100644<br>--- a/addons/cdr_mysql.c<br>+++ b/addons/cdr_mysql.c<br>@@ -128,7 +128,7 @@<br> else<br> snprintf(status, 255, "Connected to %s@%s", ast_str_buffer(dbname), ast_str_buffer(hostname));<br> <br>- if (!ast_strlen_zero(ast_str_buffer(dbuser)))<br>+ if (ast_str_strlen(dbuser))<br> snprintf(status2, 99, " with username %s", ast_str_buffer(dbuser));<br> if (ast_str_strlen(dbtable))<br> snprintf(status2, 99, " using table %s", ast_str_buffer(dbtable));<br>@@ -157,6 +157,16 @@<br> static struct ast_cli_entry cdr_mysql_status_cli[] = {<br> AST_CLI_DEFINE(handle_cli_cdr_mysql_status, "Show connection status of cdr_mysql"),<br> };<br>+<br>+static void configure_connection_charset(void)<br>+{<br>+ if (ast_str_strlen(dbcharset)) {<br>+ const char *charset = ast_str_buffer(dbcharset);<br>+ if (mysql_options(&mysql, MYSQL_SET_CHARSET_NAME, charset)) {<br>+ ast_log(LOG_WARNING, "Failed to set connection charset. Data inserted might be invalid.\n");<br>+ }<br>+ }<br>+}<br> <br> static int mysql_log(struct ast_cdr *cdr)<br> {<br>@@ -190,15 +200,13 @@<br> if (ssl_ca || ssl_cert || ssl_key) {<br> mysql_ssl_set(&mysql, ssl_key ? ast_str_buffer(ssl_key) : NULL, ssl_cert ? ast_str_buffer(ssl_cert) : NULL, ssl_ca ? ast_str_buffer(ssl_ca) : NULL, NULL, NULL);<br> }<br>+<br>+ configure_connection_charset();<br>+<br> if (mysql_real_connect(&mysql, ast_str_buffer(hostname), ast_str_buffer(dbuser), ast_str_buffer(password), ast_str_buffer(dbname), dbport, dbsock && ast_str_strlen(dbsock) ? ast_str_buffer(dbsock) : NULL, ssl_ca ? CLIENT_SSL : 0)) {<br> connected = 1;<br> connect_time = time(NULL);<br> records = 0;<br>- if (dbcharset) {<br>- ast_str_set(&sql1, 0, "SET NAMES '%s'", ast_str_buffer(dbcharset));<br>- mysql_real_query(&mysql, ast_str_buffer(sql1), ast_str_strlen(sql1));<br>- ast_debug(1, "SQL command as follows: %s\n", ast_str_buffer(sql1));<br>- }<br> } else {<br> ast_log(LOG_ERROR, "Cannot connect to database server %s: (%d) %s\n", ast_str_buffer(hostname), mysql_errno(&mysql), mysql_error(&mysql));<br> connected = 0;<br>@@ -500,7 +508,7 @@<br> res |= my_load_config_string(cfg, "global", "ssl_cert", &ssl_cert, "");<br> res |= my_load_config_string(cfg, "global", "ssl_key", &ssl_key, "");<br> <br>- res |= my_load_config_number(cfg, "global", "port", &dbport, 0);<br>+ res |= my_load_config_number(cfg, "global", "port", &dbport, MYSQL_PORT);<br> res |= my_load_config_number(cfg, "global", "timeout", &timeout, 0);<br> res |= my_load_config_string(cfg, "global", "compat", &compat, "no");<br> res |= my_load_config_string(cfg, "global", "cdrzone", &cdrzone, "");<br>@@ -540,15 +548,16 @@<br> ast_debug(1, "Got hostname of %s\n", ast_str_buffer(hostname));<br> ast_debug(1, "Got port of %d\n", dbport);<br> ast_debug(1, "Got a timeout of %d\n", timeout);<br>- if (dbsock)<br>+ if (ast_str_strlen(dbsock)) {<br> ast_debug(1, "Got sock file of %s\n", ast_str_buffer(dbsock));<br>+ }<br> ast_debug(1, "Got user of %s\n", ast_str_buffer(dbuser));<br> ast_debug(1, "Got dbname of %s\n", ast_str_buffer(dbname));<br> ast_debug(1, "Got password of %s\n", ast_str_buffer(password));<br> ast_debug(1, "%sunning in calldate compatibility mode\n", calldate_compat ? "R" : "Not r");<br> ast_debug(1, "Dates and times are localized to %s\n", S_OR(ast_str_buffer(cdrzone), "local timezone"));<br> <br>- if (dbcharset) {<br>+ if (ast_str_strlen(dbcharset)) {<br> ast_debug(1, "Got DB charset of %s\n", ast_str_buffer(dbcharset));<br> }<br> <br>@@ -573,6 +582,9 @@<br> NULL, NULL);<br> }<br> temp = dbsock && ast_str_strlen(dbsock) ? ast_str_buffer(dbsock) : NULL;<br>+<br>+ configure_connection_charset();<br>+<br> if (!mysql_real_connect(&mysql, ast_str_buffer(hostname), ast_str_buffer(dbuser), ast_str_buffer(password), ast_str_buffer(dbname), dbport, temp, ssl_ca && ast_str_strlen(ssl_ca) ? CLIENT_SSL : 0)) {<br> ast_log(LOG_ERROR, "Failed to connect to mysql database %s on %s.\n", ast_str_buffer(dbname), ast_str_buffer(hostname));<br> connected = 0;<br>@@ -582,11 +594,6 @@<br> connected = 1;<br> records = 0;<br> connect_time = time(NULL);<br>- if (dbcharset) {<br>- snprintf(sqldesc, sizeof(sqldesc), "SET NAMES '%s'", ast_str_buffer(dbcharset));<br>- mysql_real_query(&mysql, sqldesc, strlen(sqldesc));<br>- ast_debug(1, "SQL command as follows: %s\n", sqldesc);<br>- }<br> <br> /* Get table description */<br> snprintf(sqldesc, sizeof(sqldesc), "DESC %s", dbtable ? ast_str_buffer(dbtable) : "cdr");<br></pre><p>To view, visit <a href="https://gerrit.asterisk.org/7756">change 7756</a>. To unsubscribe, visit <a href="https://gerrit.asterisk.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://gerrit.asterisk.org/7756"/><meta itemprop="name" content="View Change"/></div></div>
<div style="display:none"> Gerrit-Project: asterisk </div>
<div style="display:none"> Gerrit-Branch: 13 </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>
<div style="display:none"> Gerrit-Change-Id: I36bf8dc5d5f83584e803b3b1a151dea9396ab8f5 </div>
<div style="display:none"> Gerrit-Change-Number: 7756 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: Sean Bright <sean.bright@gmail.com> </div>