Changeset 561 for trunk/src/sql/drivers/odbc
- Timestamp:
- Feb 11, 2010, 11:19:06 PM (15 years ago)
- Location:
- trunk
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk
-
Property svn:mergeinfo
set to (toggle deleted branches)
/branches/vendor/nokia/qt/4.6.1 merged eligible /branches/vendor/nokia/qt/current merged eligible /branches/vendor/trolltech/qt/current 3-149
-
Property svn:mergeinfo
set to (toggle deleted branches)
-
trunk/src/sql/drivers/odbc/qsql_odbc.cpp
r2 r561 2 2 ** 3 3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). 4 ** Contact: Qt Software Information ([email protected]) 4 ** All rights reserved. 5 ** Contact: Nokia Corporation ([email protected]) 5 6 ** 6 7 ** This file is part of the QtSql module of the Qt Toolkit. … … 21 22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. 22 23 ** 23 ** In addition, as a special exception, Nokia gives you certain 24 ** additional rights. These rights are described in the Nokia Qt LGPL 25 ** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this 26 ** package. 24 ** In addition, as a special exception, Nokia gives you certain additional 25 ** rights. These rights are described in the Nokia Qt LGPL Exception 26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. 27 27 ** 28 28 ** GNU General Public License Usage … … 34 34 ** met: http://www.gnu.org/copyleft/gpl.html. 35 35 ** 36 ** If you are unsure which license is appropriate for your use, please37 ** contact the sales department at qt-sales@nokia.com.36 ** If you 37 ** @nokia.com. 38 38 ** $QT_END_LICENSE$ 39 39 ** … … 56 56 #include <qvector.h> 57 57 #include <QDebug> 58 58 59 59 60 QT_BEGIN_NAMESPACE … … 70 71 71 72 // newer platform SDKs use SQLLEN instead of SQLINTEGER 72 #if defined(SQLLEN) || defined(Q_OS_WIN64) 73 #if defined(WIN32) && (_MSC_VER < 1300) 74 # define QSQLLEN SQLINTEGER 75 # define QSQLULEN SQLUINTEGER 76 #else 73 77 # define QSQLLEN SQLLEN 74 #else75 # define QSQLLEN SQLINTEGER76 #endif77 78 #if defined(SQLULEN) || defined(Q_OS_WIN64)79 78 # define QSQLULEN SQLULEN 80 #else 81 # define QSQLULEN SQLUINTEGER 82 #endif 79 #endif 80 83 81 84 82 static const int COLNAMESIZE = 256; … … 89 87 { 90 88 public: 89 91 90 QODBCDriverPrivate() 92 91 : hEnv(0), hDbc(0), useSchema(false), disconnectCount(0), isMySqlServer(false), 93 isMSSqlServer(false), hasSQLFetchScroll(true), hasMultiResultSets(false) 92 isMSSqlServer(false), hasSQLFetchScroll(true), hasMultiResultSets(false), 93 isQuoteInitialized(false), quote(QLatin1Char('"')) 94 94 { 95 sql_char_type = sql_varchar_type = sql_longvarchar_type = QVariant::ByteArray;96 95 unicode = false; 97 96 } … … 102 101 uint unicode :1; 103 102 uint useSchema :1; 104 QVariant::Type sql_char_type;105 QVariant::Type sql_varchar_type;106 QVariant::Type sql_longvarchar_type;107 103 int disconnectCount; 108 104 bool isMySqlServer; … … 120 116 void splitTableQualifier(const QString &qualifier, QString &catalog, 121 117 QString &schema, QString &table); 118 119 120 121 122 123 122 124 }; 123 125 … … 125 127 { 126 128 public: 127 QODBCPrivate( )128 : h Env(0), hDbc(0), hStmt(0), useSchema(false), hasSQLFetchScroll(true), precisionPolicy(QSql::HighPrecision)129 QODBCPrivate() 130 : h) 129 131 { 130 sql_char_type = sql_varchar_type = sql_longvarchar_type = QVariant::ByteArray;131 132 unicode = false; 132 133 } … … 135 136 { fieldCache.fill(QVariant()); fieldCacheIdx = 0; } 136 137 137 SQLHANDLE hEnv;138 SQLHANDLE hDbc;138 SQLHANDLE 139 SQLHANDLE 139 140 SQLHANDLE hStmt; 140 141 141 142 uint unicode :1; 142 143 uint useSchema :1; 143 QVariant::Type sql_char_type;144 QVariant::Type sql_varchar_type;145 QVariant::Type sql_longvarchar_type;146 144 147 145 QSqlRecord rInf; … … 150 148 int disconnectCount; 151 149 bool hasSQLFetchScroll; 152 QSql::NumericalPrecisionPolicy precisionPolicy; 150 QODBCDriverPrivate *driverPrivate; 151 bool userForwardOnly; 153 152 154 153 bool isStmtHandleValid(const QSqlDriver *driver); … … 174 173 SQLRETURN r = SQL_NO_DATA; 175 174 SQLTCHAR state_[SQL_SQLSTATE_SIZE+1]; 176 SQLTCHAR description_[SQL_MAX_MESSAGE_LENGTH];175 ; 177 176 QString result; 178 177 int i = 1; 179 178 180 179 description_[0] = 0; 180 181 182 183 184 185 186 187 188 189 190 181 191 do { 182 192 r = SQLGetDiagRec(handleType, 183 193 handle, 184 194 i, 185 (SQLTCHAR*)state_,195 state_, 186 196 &nativeCode_, 187 (SQLTCHAR*)description_,188 SQL_MAX_MESSAGE_LENGTH, /* in bytes, not in characters */197 , 198 189 199 &msgLen); 190 200 if (r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) { … … 193 203 QString tmpstore; 194 204 #ifdef UNICODE 195 tmpstore = QString((const QChar*)description_ , msgLen);205 tmpstore = QString((const QChar*)description_, msgLen); 196 206 #else 197 tmpstore = QString::fromLocal8Bit((const char*)description_ , msgLen);207 tmpstore = QString::fromLocal8Bit((const char*)description_, msgLen); 198 208 #endif 199 209 if(result != tmpstore) { … … 212 222 static QString qODBCWarn(const QODBCPrivate* odbc, int *nativeCode = 0) 213 223 { 214 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc-> hEnv) + QLatin1String(" ")215 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc-> hDbc) + QLatin1String(" ")224 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->) 225 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc->) 216 226 + qWarnODBCHandle(SQL_HANDLE_STMT, odbc->hStmt, nativeCode)); 217 227 } … … 219 229 static QString qODBCWarn(const QODBCDriverPrivate* odbc, int *nativeCode = 0) 220 230 { 221 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->hEnv) + QLatin1 String(" ")231 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->hEnv) + QLatin1) 222 232 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc->hDbc, nativeCode)); 223 233 } … … 251 261 static QVariant::Type qDecodeODBCType(SQLSMALLINT sqltype, const T* p, bool isSigned = true) 252 262 { 263 253 264 QVariant::Type type = QVariant::Invalid; 254 265 switch (sqltype) { … … 263 274 case SQL_INTEGER: 264 275 case SQL_BIT: 276 277 265 278 case SQL_TINYINT: 266 type = isSigned ? QVariant::Int :QVariant::UInt;279 type = QVariant::UInt; 267 280 break; 268 281 case SQL_BIGINT: … … 294 307 #endif 295 308 case SQL_CHAR: 296 type = p->sql_char_type;297 break;298 309 case SQL_VARCHAR: 299 310 case SQL_GUID: 300 type = p->sql_varchar_type;301 break;302 311 case SQL_LONGVARCHAR: 303 type = p->sql_longvarchar_type;312 type = ; 304 313 break; 305 314 default: … … 327 336 } 328 337 } 329 char* buf = new char[colSize];338 ; 330 339 while (true) { 331 340 r = SQLGetData(hStmt, 332 341 column+1, 333 342 unicode ? SQL_C_WCHAR : SQL_C_CHAR, 334 (SQLPOINTER)buf ,343 (SQLPOINTER)buf, 335 344 colSize, 336 345 &lengthIndicator); … … 347 356 int rSize = (r == SQL_SUCCESS_WITH_INFO) ? (unicode ? colSize-2 : colSize-1) : lengthIndicator; 348 357 if (unicode) { 349 fieldVal += QString(( QChar*) buf, rSize / 2);358 fieldVal += QString((, rSize / 2); 350 359 } else { 351 fieldVal += QString::fromAscii(buf , rSize);360 fieldVal += QString::fromAscii(buf, rSize); 352 361 } 353 if (fieldVal.size() + lengthIndicator >= colSize) { 362 memset(buf.data(), 0, colSize); 363 if (lengthIndicator < colSize) { 354 364 // workaround for Drivermanagers that don't return SQL_NO_DATA 355 365 break; … … 363 373 } 364 374 } 365 delete[] buf;366 375 return fieldVal; 367 376 } … … 443 452 } 444 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 445 474 static QVariant qGetBigIntData(SQLHANDLE hStmt, int column, bool isSigned = true) 446 475 { … … 552 581 if (connOpts.contains(QLatin1String("SQL_ATTR_ODBC_VERSION=SQL_OV_ODBC3"), Qt::CaseInsensitive)) 553 582 return SQL_OV_ODBC3; 554 #endif 583 #endif 555 584 return SQL_OV_ODBC2; 556 585 } 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 557 607 558 608 bool QODBCDriverPrivate::setConnectionOptions(const QString& connOpts) … … 706 756 } 707 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 708 811 //////////////////////////////////////////////////////////////////////////// 709 812 … … 711 814 : QSqlResult(db) 712 815 { 713 d = new QODBCPrivate(); 714 d->hEnv = p->hEnv; 715 d->hDbc = p->hDbc; 816 d = new QODBCPrivate(p); 716 817 d->unicode = p->unicode; 717 818 d->useSchema = p->useSchema; 718 d->sql_char_type = p->sql_char_type;719 d->sql_varchar_type = p->sql_varchar_type;720 d->sql_longvarchar_type = p->sql_longvarchar_type;721 819 d->disconnectCount = p->disconnectCount; 722 820 d->hasSQLFetchScroll = p->hasSQLFetchScroll; … … 754 852 } 755 853 r = SQLAllocHandle(SQL_HANDLE_STMT, 756 d-> hDbc,854 d->, 757 855 &d->hStmt); 758 856 if (r != SQL_SUCCESS) { … … 763 861 d->updateStmtHandleState(driver()); 764 862 765 if ( isForwardOnly()) {863 if () { 766 864 r = SQLSetStmtAttr(d->hStmt, 767 865 SQL_ATTR_CURSOR_TYPE, … … 796 894 return false; 797 895 } 896 897 898 899 900 798 901 799 902 SQLSMALLINT count; … … 883 986 SQL_FETCH_FIRST, 884 987 0); 885 if (r != SQL_SUCCESS) { 988 if (r != SQL_SUCCESS) { 886 989 if (r != SQL_NO_DATA) 887 990 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 902 1005 SQL_FETCH_PRIOR, 903 1006 0); 904 if (r != SQL_SUCCESS) { 1007 if (r != SQL_SUCCESS) { 905 1008 if (r != SQL_NO_DATA) 906 1009 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 933 1036 SQL_FETCH_LAST, 934 1037 0); 935 if (r != SQL_SUCCESS) { 1038 if (r != SQL_SUCCESS) { 936 1039 if (r != SQL_NO_DATA) 937 1040 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 1024 1127 break; 1025 1128 case QVariant::String: 1026 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), true);1129 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), e); 1027 1130 break; 1028 1131 case QVariant::Double: 1029 { 1030 QString value=qGetStringData(d->hStmt, i, info.length(), false); 1031 bool ok=false; 1032 switch(d->precisionPolicy) { 1033 case QSql::LowPrecisionInt32: 1034 d->fieldCache[i] = value.toInt(&ok); 1035 break; 1036 case QSql::LowPrecisionInt64: 1037 d->fieldCache[i] = value.toLongLong(&ok); 1038 break; 1039 case QSql::LowPrecisionDouble: 1040 d->fieldCache[i] = value.toDouble(&ok); 1041 break; 1042 case QSql::HighPrecision: 1043 default: 1044 d->fieldCache[i] = value; 1045 ok=true; 1046 break; 1047 } 1048 if(ok==false) 1049 d->fieldCache[i] = QVariant(); 1050 break; 1132 switch(numericalPrecisionPolicy()) { 1133 case QSql::LowPrecisionInt32: 1134 d->fieldCache[i] = qGetIntData(d->hStmt, i); 1135 break; 1136 case QSql::LowPrecisionInt64: 1137 d->fieldCache[i] = qGetBigIntData(d->hStmt, i); 1138 break; 1139 case QSql::LowPrecisionDouble: 1140 d->fieldCache[i] = qGetDoubleData(d->hStmt, i); 1141 break; 1142 case QSql::HighPrecision: 1143 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), false); 1144 break; 1051 1145 } 1146 1052 1147 default: 1053 1148 d->fieldCache[i] = QVariant(qGetStringData(d->hStmt, i, info.length(), false)); … … 1103 1198 } 1104 1199 r = SQLAllocHandle(SQL_HANDLE_STMT, 1105 d-> hDbc,1200 d->, 1106 1201 &d->hStmt); 1107 1202 if (r != SQL_SUCCESS) { … … 1112 1207 d->updateStmtHandleState(driver()); 1113 1208 1114 if ( isForwardOnly()) {1209 if () { 1115 1210 r = SQLSetStmtAttr(d->hStmt, 1116 1211 SQL_ATTR_CURSOR_TYPE, … … 1372 1467 #endif 1373 1468 { 1374 QByteArray str = val.toString().to Utf8();1469 QByteArray str = val.toString().to(); 1375 1470 if (*ind != SQL_NULL_DATA) 1376 1471 *ind = str.length(); 1377 1472 int strSize = str.length(); 1378 1473 1379 1474 r = SQLBindParameter(d->hStmt, 1380 1475 i + 1, … … 1423 1518 } 1424 1519 1520 1521 1522 1523 1524 1425 1525 SQLSMALLINT count; 1426 1526 SQLNumResultCols(d->hStmt, &count); … … 1457 1557 QTime(dt.hour, dt.minute, dt.second, dt.fraction / 1000000))); 1458 1558 break; } 1559 1459 1560 case QVariant::Int: 1460 1561 case QVariant::UInt: … … 1546 1647 *static_cast<bool*>(data) = nextResult(); 1547 1648 break; 1548 case QSqlResult::SetNumericalPrecision:1549 Q_ASSERT(data);1550 d->precisionPolicy = *reinterpret_cast<QSql::NumericalPrecisionPolicy *>(data);1551 break;1552 1649 default: 1553 1650 QSqlResult::virtual_hook(id, data); 1554 1651 } 1652 1653 1654 1655 1656 1657 1555 1658 } 1556 1659 … … 1670 1773 if (db.contains(QLatin1String(".dsn"), Qt::CaseInsensitive)) 1671 1774 connQStr = QLatin1String("FILEDSN=") + db; 1672 else if (db.contains(QLatin1String("DRIVER="), Qt::CaseInsensitive) 1775 else if (db.contains(QLatin1String("DRIVER="), Qt::CaseInsensitive) 1673 1776 || db.contains(QLatin1String("SERVER="), Qt::CaseInsensitive)) 1674 1777 connQStr = db; … … 1680 1783 if (!password.isEmpty()) 1681 1784 connQStr += QLatin1String(";PWD=") + password; 1682 1785 1683 1786 SQLSMALLINT cb; 1684 1787 SQLTCHAR connOut[1024]; … … 1703 1806 if (!d->checkDriver()) { 1704 1807 setLastError(qMakeError(tr("Unable to connect - Driver doesn't support all " 1705 " needed functionality"), QSqlError::ConnectionError, d));1808 ""), QSqlError::ConnectionError, d)); 1706 1809 setOpenError(true); 1707 1810 return false; … … 1715 1818 setOpen(true); 1716 1819 setOpenError(false); 1820 1821 1822 1823 1717 1824 return true; 1718 1825 } … … 1763 1870 return; 1764 1871 #endif 1765 #if defined(Q_WS_WIN) 1766 QT_WA( 1767 {}, 1768 { 1769 unicode = false; 1770 return; 1771 }) 1772 #endif 1872 1773 1873 SQLRETURN r; 1774 1874 SQLUINTEGER fFunc; … … 1781 1881 NULL); 1782 1882 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WCHAR)) { 1783 sql_char_type = QVariant::String;1784 1883 unicode = true; 1785 1884 } … … 1791 1890 NULL); 1792 1891 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WVARCHAR)) { 1793 sql_varchar_type = QVariant::String;1794 1892 unicode = true; 1795 1893 } … … 1801 1899 NULL); 1802 1900 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WLONGVARCHAR)) { 1803 sql_longvarchar_type = QVariant::String;1804 1901 unicode = true; 1805 1902 } … … 2085 2182 QString catalog, schema, table; 2086 2183 d->splitTableQualifier(tablename, catalog, schema, table); 2184 2185 2186 2187 2188 2189 2190 2191 2192 2193 2194 2195 2196 2197 2198 2199 2087 2200 r = SQLSetStmtAttr(hStmt, 2088 2201 SQL_ATTR_CURSOR_TYPE, … … 2187 2300 QString catalog, schema, table; 2188 2301 d->splitTableQualifier(tablename, catalog, schema, table); 2302 2303 2304 2305 2306 2307 2308 2309 2310 2311 2312 2313 2314 2315 2316 2317 2189 2318 SQLRETURN r = SQLAllocHandle(SQL_HANDLE_STMT, 2190 2319 d->hDbc, … … 2294 2423 QString QODBCDriver::escapeIdentifier(const QString &identifier, IdentifierType) const 2295 2424 { 2425 2296 2426 QString res = identifier; 2297 if (d->isMySqlServer) { 2298 if(!identifier.isEmpty() && identifier.left(1) != QString(QLatin1Char('`')) && identifier.right(1) != QString(QLatin1Char('`')) ) { 2299 res.prepend(QLatin1Char('`')).append(QLatin1Char('`')); 2300 res.replace(QLatin1Char('.'), QLatin1String("`.`")); 2301 } 2302 } else { 2303 if(!identifier.isEmpty() && identifier.left(1) != QString(QLatin1Char('"')) && identifier.right(1) != QString(QLatin1Char('"')) ) { 2304 res.replace(QLatin1Char('"'), QLatin1String("\"\"")); 2305 res.prepend(QLatin1Char('"')).append(QLatin1Char('"')); 2306 res.replace(QLatin1Char('.'), QLatin1String("\".\"")); 2307 } 2427 if(!identifier.isEmpty() && !identifier.startsWith(quote) && !identifier.endsWith(quote) ) { 2428 res.replace(quote, QString(quote)+QString(quote)); 2429 res.prepend(quote).append(quote); 2430 res.replace(QLatin1Char('.'), QString(quote)+QLatin1Char('.')+QString(quote)); 2308 2431 } 2309 2432 return res; 2310 2433 } 2311 2434 2435 2436 2437 2438 2439 2440 2441 2442 2312 2443 QT_END_NAMESPACE -
trunk/src/sql/drivers/odbc/qsql_odbc.h
r2 r561 2 2 ** 3 3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). 4 ** Contact: Qt Software Information ([email protected]) 4 ** All rights reserved. 5 ** Contact: Nokia Corporation ([email protected]) 5 6 ** 6 7 ** This file is part of the QtSql module of the Qt Toolkit. … … 21 22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. 22 23 ** 23 ** In addition, as a special exception, Nokia gives you certain 24 ** additional rights. These rights are described in the Nokia Qt LGPL 25 ** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this 26 ** package. 24 ** In addition, as a special exception, Nokia gives you certain additional 25 ** rights. These rights are described in the Nokia Qt LGPL Exception 26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. 27 27 ** 28 28 ** GNU General Public License Usage … … 34 34 ** met: http://www.gnu.org/copyleft/gpl.html. 35 35 ** 36 ** If you are unsure which license is appropriate for your use, please37 ** contact the sales department at qt-sales@nokia.com.36 ** If you 37 ** @nokia.com. 38 38 ** $QT_END_LICENSE$ 39 39 ** … … 101 101 102 102 QVariant handle() const; 103 103 104 104 105 protected: … … 146 147 QString escapeIdentifier(const QString &identifier, IdentifierType type) const; 147 148 149 150 151 148 152 protected: 149 153 bool beginTransaction(); 150 154 bool commitTransaction(); 151 155 bool rollbackTransaction(); 156 152 157 private: 153 158 void init();
Note:
See TracChangeset
for help on using the changeset viewer.