ODBC: Remove the trailing \0 in the case of a non unicode string

Some ODBC drivers, such as old Informix ODBC drivers will incorrectly
include a trailing \0 in a string when this should not exist. For
unicode strings this was already accounted for, but for non-unicode ones
this was not covered.

The change also fixes up the comments a bit to make this clearer and
also added one for the unicode case.

Task-number: QTBUG-62406
Change-Id: Id932a58d9e5fdff2f4d1aacf8cc9fdaeb34f95f4
Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
This commit is contained in:
Andy Shaw 2018-09-06 12:39:31 +02:00
parent d8c210d7f5
commit a3e8b92d97

View File

@ -72,6 +72,7 @@ inline static QString fromSQLTCHAR(const QVarLengthArray<SQLTCHAR>& input, int s
{ {
QString result; QString result;
// Remove any trailing \0 as some drivers misguidedly append one
int realsize = qMin(size, input.size()); int realsize = qMin(size, input.size());
if(realsize > 0 && input[realsize-1] == 0) if(realsize > 0 && input[realsize-1] == 0)
realsize--; realsize--;
@ -458,7 +459,6 @@ static QString qGetStringData(SQLHANDLE hStmt, int column, int colSize, bool uni
// more data can be fetched, the length indicator does NOT // more data can be fetched, the length indicator does NOT
// contain the number of bytes returned - it contains the // contain the number of bytes returned - it contains the
// total number of bytes that CAN be fetched // total number of bytes that CAN be fetched
// colSize-1: remove 0 termination when there is more data to fetch
int rSize = (r == SQL_SUCCESS_WITH_INFO) ? colSize : int(lengthIndicator / sizeof(SQLTCHAR)); int rSize = (r == SQL_SUCCESS_WITH_INFO) ? colSize : int(lengthIndicator / sizeof(SQLTCHAR));
fieldVal += fromSQLTCHAR(buf, rSize); fieldVal += fromSQLTCHAR(buf, rSize);
if (lengthIndicator < SQLLEN(colSize*sizeof(SQLTCHAR))) { if (lengthIndicator < SQLLEN(colSize*sizeof(SQLTCHAR))) {
@ -499,9 +499,12 @@ static QString qGetStringData(SQLHANDLE hStmt, int column, int colSize, bool uni
// more data can be fetched, the length indicator does NOT // more data can be fetched, the length indicator does NOT
// contain the number of bytes returned - it contains the // contain the number of bytes returned - it contains the
// total number of bytes that CAN be fetched // total number of bytes that CAN be fetched
// colSize-1: remove 0 termination when there is more data to fetch
int rSize = (r == SQL_SUCCESS_WITH_INFO) ? colSize : lengthIndicator; int rSize = (r == SQL_SUCCESS_WITH_INFO) ? colSize : lengthIndicator;
fieldVal += QString::fromUtf8((const char *)buf.constData(), rSize); // Remove any trailing \0 as some drivers misguidedly append one
int realsize = qMin(rSize, buf.size());
if (realsize > 0 && buf[realsize - 1] == 0)
realsize--;
fieldVal += QString::fromUtf8(reinterpret_cast<const char *>(buf.constData()), realsize);
if (lengthIndicator < SQLLEN(colSize)) { if (lengthIndicator < SQLLEN(colSize)) {
// workaround for Drivermanagers that don't return SQL_NO_DATA // workaround for Drivermanagers that don't return SQL_NO_DATA
break; break;