[MDEV-9415] Crash with ConnectSE + MySQL ODBC driver + INSERT Created: 2016-01-14 Updated: 2017-11-05 |
|
| Status: | Open |
| Project: | MariaDB Server |
| Component/s: | None |
| Affects Version/s: | 10.1 |
| Fix Version/s: | 10.1 |
| Type: | Bug | Priority: | Major |
| Reporter: | Alexander Barkov | Assignee: | Olivier Bertrand |
| Resolution: | Unresolved | Votes: | 1 |
| Labels: | None | ||
| Attachments: |
|
||||||||
| Issue Links: |
|
||||||||
| Description |
|
I create a table on a remote MySQL server:
and create a ConnectSE connection on a local server:
It works fine. Now if I try to insert more rows into this table:
it crashes with this stack trace:
After installing debug packages:
the stack trace is more readable:
If I start the server with valgrind: "valgrind --tool=memcheck ./mysqld" and run the same INSERT query, it crashes with the following comments.
The crash seems to be repeatable with 10.0 and 10.1. |
| Comments |
| Comment by Alexander Barkov [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
DELETE seems to work fine:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
UPDATE also seems to work fine:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
INSERT with a PostgreSQL data source seems to work fine. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Olivier Bertrand [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
As in MDEV-9414, it seems dependant on the used connector. Using the MySQL connector 5.3 the INSERT statement worked fine. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
The returned info in the DELETE and UPDATE examples above (delete reproduced below) don't seem exactly right to me. The result says "Query OK, 0 rows affected, 1 warning" and then SHOW WARNINGS shows 1 row affected. Shouldn't the result be "Query OK, 1 rows affected, 0 warning" ? I get this same behavior using the TDS ODBC driver, so it does not appear to be driver specific. Should this be opened as a separate issue, or am I missing something? This behavior is causing problems for our app as well.
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
We are hoping to use CONNECT with many different drivers, so testing for this and providing a fall back would be helpful. Basically make it as tolerant of drivers as possible. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Olivier Bertrand [ 2016-01-14 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
About warnings: yes it should be like you say. Unfortunately Connect cannot change the message returned by MariaDB and for MariaDB there are 0 row affected in the Connect table that is not modified. Indeed this is the remote table that is modified. Yes, I try to make Connect as tolerant of drivers as possible and this is the experience of users such as yourself that can show where and when there are problems. In the present case, we are in a situation because Alexander and I are unable to reproduce the bugs you have. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-02 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Would it be possible to provide UnixODBC trace for the crash? | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-02 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
How do I get the trace? | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-03 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Add Trace=On/Yes/1 and TraceFile=/path/to/logfile to the your dsn section in odbc.ini | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-20 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Lawrin, Sorry for the delay. Here's the trace.
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-21 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Hmm, it doesn't get any more clear. I will look in it some more though. And it looks like it crashes with both mysql's and mariadb's libmysql. Also I can offer a workaround. Add to the DSN used NO_SSPS=1 And speakin about the DSN("myodbc") - I guess there is no fancy options in it, other than user credentials? | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Olivier Bertrand [ 2016-02-22 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Looking in debug mode at what Connect does when inserting in a table I noted this. After calling SQLPrepare, Connect uses this function to bind the parameters:
When the server implements SQLDescribeParam (as Oracle does) this function is used and when it is not implemented (for instance by Microsoft Access) Connect tries to retrieve the parameters values from the column definition. Until now this worked fine, however there is a problem with the MySQL connector. Apparently it does implement that function (rc=0) but wrongly does not set all the given arguments. In particular colsize and dec are not set and keep there value. As they are not intitialized in their declaration, these values are trash and they are used in the call to SQLBindParameter. Strangely enough this does not do anything wrong on Windows so I cannot be sure this is the cause of your problem. Alexander, can you test that fixing this (for instance by giving an initial value to these variables, perhaps the one coming from the column definition) solves the problem. If so, this would not be a bug only of Connect but also of the MySQL connector. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-22 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
But connector crashes in the SQLPrepare call. Thus I do not think it has anything to do with SQLDescribeParam As for its implementation im MySQL(and in MariaDB) - it's nothing more than giving default values good and safe for general case. e.g. it always return type SQL_VARCHAR, thus dec value is irrelevant. Colsize is always set though. And there is no better way to implement it with MariaDB/MySQL. At least at the moment. And I would not recommend to use it for param binding. There are usually better information sources for this purpose. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Olivier Bertrand [ 2016-02-22 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Sure enough. But in that case it would be better not to implement it at all. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-22 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Well, connectors require it to comply with specs. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-02-23 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
I thought the following might help... NOTE this happened with the DSN having NO_SSPS=1 (on CentOS7 on Google Cloud)
but when you try to get the list of tables:
... and the server has crashed. [MySQL] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-23 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
I am curious what happens in this case - is it possible to see the backtrace? However iirc in this case SSPS would not be engaged even if NO_SSPS was set to 0 | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-23 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Yes, I have verified that if there is no parameter placeholders in the query, myodbc will prepare it on the client side. thus it is even more curious, since in original report 'select * from t1' works fine | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-02-23 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
BTW typing help in isql or iusql both return the list of table successfully. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-02-23 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
What file would contain the backtrace? | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Adding this line
into odbc.ini helps. Robert, looks like a good temporary workaround. We'll continue studying the problem in the meanwhile. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Lawrin, The odbc.ini entry looks like this:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Olivier, I tried to set a break point in ODBConn::BindParam(). It crashes in ODBConn::PrepareSQL(). I guess, ODBConn::BindParam() is to be called after ODBConn::PrepareSQL(). | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
The same script does not crash for me:
It returns an error instead:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
As for NO_SSPS=1 being temporary solution. In fact in many, if not in most, cases it should be even beneficial performance wise. Only if prepared statements re-used many times, they would be faster than client side emulation. Here we(well, Georg) also got the same error, but seems that server crashes - on 2nd query it is away already. Or it crashes on 2nd query. MariaDB [test]> create table t1(a int) ENGINE=Connect TABLE_TYPE=ODBC CATFUNC=TABLES CONNECTION='dsn=connect_test;UID=root;'; MariaDB [test]> select * from t1; | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Olivier Bertrand [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Invalid flag 0 for column a | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-02-24 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Yes, I saw that too....the following
should be:
This works with all other ODBC drivers I have tried except MySQL. I have also attached a new trace from unixodbc in case there is any useful info there. log224-unixodbc.log Not knowing anything about the internals of all this, it would seem like there is a global variable that is colliding between client and server... so the mysql client code works fine when running in its own execution space, but when running within the mysql server execution space has a possible variable/symbol conflict. Since connect is probably the first use case where the client and server code are running in the same execution space, you can see where this would find the problem. Just speculation on my part that might trigger a thought by someone who actually knows this stuff. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-02-26 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Sorry for confusing.
with the current sources, both 10.0 and 10.1. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-02-26 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Alex, May I ask what OS and unixODBC version you are using? | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-03-01 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Can somebody try if myodbc connector from mysql site makes difference for this issue? The difference is that mysql is linking against mysqlclient statically, when builds binaries. While linux distributions hate static linking, and connectors they provide are linked against libmysql dynamically. | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Robert Dyas [ 2016-03-02 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
I have tried the MySQL ODBC driver 5.3 (both unicode and ansi) downloaded from the Oracle website...crashes the server.
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Alexander Barkov [ 2016-03-04 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
I tried mysql-connector-odbc-5.3.4-linux-glibc2.5-x86-64bit.tar.gz
it crashes on SELECT with the following stack trace:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Comment by Lawrin Novitsky [ 2016-03-04 ] | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Robert, Bar - thanks, very interesting. Especially the new backtrace. The crash occurs in different place. But here we can see that myodbc function calls my_free from the MariaDB server. |