source: trunk/src/sql/kernel/qsqldatabase.cpp@ 769

Last change on this file since 769 was 769, checked in by Dmitry A. Kuminov, 15 years ago

trunk: Merged in qt 4.6.3 sources from branches/vendor/nokia/qt.

File size: 42.8 KB
Line 
1/****************************************************************************
2**
3** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
4** All rights reserved.
5** Contact: Nokia Corporation ([email protected])
6**
7** This file is part of the QtSql module of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:LGPL$
10** Commercial Usage
11** Licensees holding valid Qt Commercial licenses may use this file in
12** accordance with the Qt Commercial License Agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in
14** a written agreement between you and Nokia.
15**
16** GNU Lesser General Public License Usage
17** Alternatively, this file may be used under the terms of the GNU Lesser
18** General Public License version 2.1 as published by the Free Software
19** Foundation and appearing in the file LICENSE.LGPL included in the
20** packaging of this file. Please review the following information to
21** ensure the GNU Lesser General Public License version 2.1 requirements
22** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
23**
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**
28** GNU General Public License Usage
29** Alternatively, this file may be used under the terms of the GNU
30** General Public License version 3.0 as published by the Free Software
31** Foundation and appearing in the file LICENSE.GPL included in the
32** packaging of this file. Please review the following information to
33** ensure the GNU General Public License version 3.0 requirements will be
34** met: http://www.gnu.org/copyleft/gpl.html.
35**
36** If you have questions regarding the use of this file, please contact
37** Nokia at [email protected].
38** $QT_END_LICENSE$
39**
40****************************************************************************/
41
42#include "qsqldatabase.h"
43#include "qsqlquery.h"
44
45#ifdef Q_OS_WIN32
46// Conflicting declarations of LPCBYTE in sqlfront.h and winscard.h
47#define _WINSCARD_H_
48#endif
49
50#ifdef QT_SQL_PSQL
51#include "../drivers/psql/qsql_psql.h"
52#endif
53#ifdef QT_SQL_MYSQL
54#include "../drivers/mysql/qsql_mysql.h"
55#endif
56#ifdef QT_SQL_ODBC
57#include "../drivers/odbc/qsql_odbc.h"
58#endif
59#ifdef QT_SQL_OCI
60#include "../drivers/oci/qsql_oci.h"
61#endif
62#ifdef QT_SQL_TDS
63#include "../drivers/tds/qsql_tds.h"
64#endif
65#ifdef QT_SQL_DB2
66#include "../drivers/db2/qsql_db2.h"
67#endif
68#ifdef QT_SQL_SQLITE
69#include "../drivers/sqlite/qsql_sqlite.h"
70#endif
71#ifdef QT_SQL_SQLITE2
72#include "../drivers/sqlite2/qsql_sqlite2.h"
73#endif
74#ifdef QT_SQL_IBASE
75#undef SQL_FLOAT // avoid clash with ODBC
76#undef SQL_DOUBLE
77#undef SQL_TIMESTAMP
78#undef SQL_TYPE_TIME
79#undef SQL_TYPE_DATE
80#undef SQL_DATE
81#define SCHAR IBASE_SCHAR // avoid clash with ODBC (older versions of ibase.h with Firebird)
82#include "../drivers/ibase/qsql_ibase.h"
83#undef SCHAR
84#endif
85
86#include "qdebug.h"
87#include "qcoreapplication.h"
88#include "qreadwritelock.h"
89#include "qsqlresult.h"
90#include "qsqldriver.h"
91#include "qsqldriverplugin.h"
92#include "qsqlindex.h"
93#include "private/qfactoryloader_p.h"
94#include "private/qsqlnulldriver_p.h"
95#include "qmutex.h"
96#include "qhash.h"
97#include <stdlib.h>
98
99QT_BEGIN_NAMESPACE
100
101#if !defined(QT_NO_LIBRARY) && !defined(QT_NO_SETTINGS)
102Q_GLOBAL_STATIC_WITH_ARGS(QFactoryLoader, loader,
103 (QSqlDriverFactoryInterface_iid,
104 QLatin1String("/sqldrivers")))
105#endif
106
107QT_STATIC_CONST_IMPL char *QSqlDatabase::defaultConnection = "qt_sql_default_connection";
108
109typedef QHash<QString, QSqlDriverCreatorBase*> DriverDict;
110
111class QConnectionDict: public QHash<QString, QSqlDatabase>
112{
113public:
114 inline bool contains_ts(const QString &key)
115 {
116 QReadLocker locker(&lock);
117 return contains(key);
118 }
119 inline QStringList keys_ts() const
120 {
121 QReadLocker locker(&lock);
122 return keys();
123 }
124
125 mutable QReadWriteLock lock;
126};
127Q_GLOBAL_STATIC(QConnectionDict, dbDict)
128
129class QSqlDatabasePrivate
130{
131public:
132 QSqlDatabasePrivate(QSqlDatabase *d, QSqlDriver *dr = 0):
133 q(d),
134 driver(dr),
135 port(-1)
136 {
137 ref = 1;
138 if(driver)
139 precisionPolicy = driver->numericalPrecisionPolicy();
140 else
141 precisionPolicy= QSql::LowPrecisionDouble;
142 }
143 QSqlDatabasePrivate(const QSqlDatabasePrivate &other);
144 ~QSqlDatabasePrivate();
145 void init(const QString& type);
146 void copy(const QSqlDatabasePrivate *other);
147 void disable();
148
149 QAtomicInt ref;
150 QSqlDatabase *q;
151 QSqlDriver* driver;
152 QString dbname;
153 QString uname;
154 QString pword;
155 QString hname;
156 QString drvName;
157 int port;
158 QString connOptions;
159 QString connName;
160 QSql::NumericalPrecisionPolicy precisionPolicy;
161
162 static QSqlDatabasePrivate *shared_null();
163 static QSqlDatabase database(const QString& name, bool open);
164 static void addDatabase(const QSqlDatabase &db, const QString & name);
165 static void removeDatabase(const QString& name);
166 static void invalidateDb(const QSqlDatabase &db, const QString &name);
167 static DriverDict &driverDict();
168 static void cleanConnections();
169};
170
171QSqlDatabasePrivate::QSqlDatabasePrivate(const QSqlDatabasePrivate &other)
172{
173 ref = 1;
174 q = other.q;
175 dbname = other.dbname;
176 uname = other.uname;
177 pword = other.pword;
178 hname = other.hname;
179 drvName = other.drvName;
180 port = other.port;
181 connOptions = other.connOptions;
182 driver = other.driver;
183 precisionPolicy = other.precisionPolicy;
184}
185
186QSqlDatabasePrivate::~QSqlDatabasePrivate()
187{
188 if (driver != shared_null()->driver)
189 delete driver;
190}
191
192void QSqlDatabasePrivate::cleanConnections()
193{
194 QConnectionDict *dict = dbDict();
195 Q_ASSERT(dict);
196 QWriteLocker locker(&dict->lock);
197
198 QConnectionDict::iterator it = dict->begin();
199 while (it != dict->end()) {
200 invalidateDb(it.value(), it.key());
201 ++it;
202 }
203 dict->clear();
204}
205
206static bool qDriverDictInit = false;
207static void cleanDriverDict()
208{
209 qDeleteAll(QSqlDatabasePrivate::driverDict());
210 QSqlDatabasePrivate::driverDict().clear();
211 QSqlDatabasePrivate::cleanConnections();
212 qDriverDictInit = false;
213}
214
215DriverDict &QSqlDatabasePrivate::driverDict()
216{
217 static DriverDict dict;
218 if (!qDriverDictInit) {
219 qDriverDictInit = true;
220 qAddPostRoutine(cleanDriverDict);
221 }
222 return dict;
223}
224
225QSqlDatabasePrivate *QSqlDatabasePrivate::shared_null()
226{
227 static QSqlNullDriver dr;
228 static QSqlDatabasePrivate n(NULL, &dr);
229 return &n;
230}
231
232void QSqlDatabasePrivate::invalidateDb(const QSqlDatabase &db, const QString &name)
233{
234 if (db.d->ref != 1) {
235 qWarning("QSqlDatabasePrivate::removeDatabase: connection '%s' is still in use, "
236 "all queries will cease to work.", name.toLocal8Bit().constData());
237 db.d->disable();
238 db.d->connName.clear();
239 }
240}
241
242void QSqlDatabasePrivate::removeDatabase(const QString &name)
243{
244 QConnectionDict *dict = dbDict();
245 Q_ASSERT(dict);
246 QWriteLocker locker(&dict->lock);
247
248 if (!dict->contains(name))
249 return;
250
251 invalidateDb(dict->take(name), name);
252}
253
254void QSqlDatabasePrivate::addDatabase(const QSqlDatabase &db, const QString &name)
255{
256 QConnectionDict *dict = dbDict();
257 Q_ASSERT(dict);
258 QWriteLocker locker(&dict->lock);
259
260 if (dict->contains(name)) {
261 invalidateDb(dict->take(name), name);
262 qWarning("QSqlDatabasePrivate::addDatabase: duplicate connection name '%s', old "
263 "connection removed.", name.toLocal8Bit().data());
264 }
265 dict->insert(name, db);
266 db.d->connName = name;
267}
268
269/*! \internal
270*/
271QSqlDatabase QSqlDatabasePrivate::database(const QString& name, bool open)
272{
273 const QConnectionDict *dict = dbDict();
274 Q_ASSERT(dict);
275
276 dict->lock.lockForRead();
277 QSqlDatabase db = dict->value(name);
278 dict->lock.unlock();
279 if (db.isValid() && !db.isOpen() && open) {
280 if (!db.open())
281 qWarning() << "QSqlDatabasePrivate::database: unable to open database:" << db.lastError().text();
282
283 }
284 return db;
285}
286
287
288/*! \internal
289 Copies the connection data from \a other.
290*/
291void QSqlDatabasePrivate::copy(const QSqlDatabasePrivate *other)
292{
293 q = other->q;
294 dbname = other->dbname;
295 uname = other->uname;
296 pword = other->pword;
297 hname = other->hname;
298 drvName = other->drvName;
299 port = other->port;
300 connOptions = other->connOptions;
301 precisionPolicy = other->precisionPolicy;
302}
303
304void QSqlDatabasePrivate::disable()
305{
306 if (driver != shared_null()->driver) {
307 delete driver;
308 driver = shared_null()->driver;
309 }
310}
311
312/*!
313 \class QSqlDriverCreatorBase
314 \brief The QSqlDriverCreatorBase class is the base class for
315 SQL driver factories.
316
317 \ingroup database
318 \inmodule QtSql
319
320 Reimplement createObject() to return an instance of the specific
321 QSqlDriver subclass that you want to provide.
322
323 See QSqlDatabase::registerSqlDriver() for details.
324
325 \sa QSqlDriverCreator
326*/
327
328/*!
329 \fn QSqlDriverCreatorBase::~QSqlDriverCreatorBase()
330
331 Destroys the SQL driver creator object.
332*/
333
334/*!
335 \fn QSqlDriver *QSqlDriverCreatorBase::createObject() const
336
337 Reimplement this function to returns a new instance of a
338 QSqlDriver subclass.
339*/
340
341/*!
342 \class QSqlDriverCreator
343 \brief The QSqlDriverCreator class is a template class that
344 provides a SQL driver factory for a specific driver type.
345
346 \ingroup database
347 \inmodule QtSql
348
349 QSqlDriverCreator<T> instantiates objects of type T, where T is a
350 QSqlDriver subclass.
351
352 See QSqlDatabase::registerSqlDriver() for details.
353*/
354
355/*!
356 \fn QSqlDriver *QSqlDriverCreator::createObject() const
357 \reimp
358*/
359
360/*!
361 \class QSqlDatabase
362 \brief The QSqlDatabase class represents a connection to
363 a database.
364
365 \ingroup database
366
367 \inmodule QtSql
368
369 The QSqlDatabase class provides an interface for accessing a
370 database through a connection. An instance of QSqlDatabase
371 represents the connection. The connection provides access to the
372 database via one of the \l{SQL Database Drivers#Supported
373 Databases} {supported database drivers}, which are derived from
374 QSqlDriver. Alternatively, you can subclass your own database
375 driver from QSqlDriver. See \l{How to Write Your Own Database
376 Driver} for more information.
377
378 Create a connection (i.e., an instance of QSqlDatabase) by calling
379 one of the static addDatabase() functions, where you specify
380 \l{SQL Database Drivers#Supported Databases} {the driver or type
381 of driver} to use (i.e., what kind of database will you access?)
382 and a connection name. A connection is known by its own name,
383 \e{not} by the name of the database it connects to. You can have
384 multiple connections to one database. QSqlDatabase also supports
385 the concept of a \e{default} connection, which is the unnamed
386 connection. To create the default connection, don't pass the
387 connection name argument when you call addDatabase().
388 Subsequently, when you call any static member function that takes
389 the connection name argument, if you don't pass the connection
390 name argument, the default connection is assumed. The following
391 snippet shows how to create and open a default connection to a
392 PostgreSQL database:
393
394 \snippet doc/src/snippets/sqldatabase/sqldatabase.cpp 0
395
396 Once the QSqlDatabase object has been created, set the connection
397 parameters with setDatabaseName(), setUserName(), setPassword(),
398 setHostName(), setPort(), and setConnectOptions(). Then call
399 open() to activate the physical connection to the database. The
400 connection is not usable until you open it.
401
402 The connection defined above will be the \e{default} connection,
403 because we didn't give a connection name to \l{QSqlDatabase::}
404 {addDatabase()}. Subsequently, you can get the default connection
405 by calling database() without the connection name argument:
406
407 \snippet doc/src/snippets/sqldatabase/sqldatabase.cpp 1
408
409 QSqlDatabase is a value class. Changes made to a database
410 connection via one instance of QSqlDatabase will affect other
411 instances of QSqlDatabase that represent the same connection. Use
412 cloneDatabase() to create an independent database connection based
413 on an existing one.
414
415 If you create multiple database connections, specify a unique
416 connection name for each one, when you call addDatabase(). Use
417 database() with a connection name to get that connection. Use
418 removeDatabase() with a connection name to remove a connection.
419 QSqlDatabase outputs a warning if you try to remove a connection
420 referenced by other QSqlDatabase objects. Use contains() to see if
421 a given connection name is in the list of connections.
422
423 Once a connection is established, you can call tables() to get the
424 list of tables in the database, call primaryIndex() to get a
425 table's primary index, and call record() to get meta-information
426 about a table's fields (e.g., field names).
427
428 \note QSqlDatabase::exec() is deprecated. Use QSqlQuery::exec()
429 instead.
430
431 If the driver supports transactions, use transaction() to start a
432 transaction, and commit() or rollback() to complete it. Use
433 \l{QSqlDriver::} {hasFeature()} to ask if the driver supports
434 transactions. \note When using transactions, you must start the
435 transaction before you create your query.
436
437 If an error occurrs, lastError() will return information about it.
438
439 Get the names of the available SQL drivers with drivers(). Check
440 for the presence of a particular driver with isDriverAvailable().
441 If you have created your own custom driver, you must register it
442 with registerSqlDriver().
443
444 \sa QSqlDriver, QSqlQuery, {QtSql Module}, {Threads and the SQL Module}
445*/
446
447/*! \fn QSqlDatabase QSqlDatabase::addDatabase(const QString &type, const QString &connectionName)
448 \threadsafe
449
450 Adds a database to the list of database connections using the
451 driver \a type and the connection name \a connectionName. If
452 there already exists a database connection called \a
453 connectionName, that connection is removed.
454
455 The database connection is referred to by \a connectionName. The
456 newly added database connection is returned.
457
458 If \a type is not available or could not be loaded, isValid() returns false.
459
460 If \a connectionName is not specified, the new connection becomes
461 the default connection for the application, and subsequent calls
462 to database() without the connection name argument will return the
463 default connection. If a \a connectionName is provided here, use
464 database(\a connectionName) to retrieve the connection.
465
466 \warning If you add a connection with the same name as an existing
467 connection, the new connection replaces the old one. If you call
468 this function more than once without specifying \a connectionName,
469 the default connection will be the one replaced.
470
471 Before using the connection, it must be initialized. e.g., call
472 some or all of setDatabaseName(), setUserName(), setPassword(),
473 setHostName(), setPort(), and setConnectOptions(), and, finally,
474 open().
475
476 \sa database() removeDatabase() {Threads and the SQL Module}
477*/
478QSqlDatabase QSqlDatabase::addDatabase(const QString &type, const QString &connectionName)
479{
480 QSqlDatabase db(type);
481 QSqlDatabasePrivate::addDatabase(db, connectionName);
482 return db;
483}
484
485/*!
486 \threadsafe
487
488 Returns the database connection called \a connectionName. The
489 database connection must have been previously added with
490 addDatabase(). If \a open is true (the default) and the database
491 connection is not already open it is opened now. If no \a
492 connectionName is specified the default connection is used. If \a
493 connectionName does not exist in the list of databases, an invalid
494 connection is returned.
495
496 \sa isOpen() {Threads and the SQL Module}
497*/
498
499QSqlDatabase QSqlDatabase::database(const QString& connectionName, bool open)
500{
501 return QSqlDatabasePrivate::database(connectionName, open);
502}
503
504/*!
505 \threadsafe
506
507 Removes the database connection \a connectionName from the list of
508 database connections.
509
510 \warning There should be no open queries on the database
511 connection when this function is called, otherwise a resource leak
512 will occur.
513
514 Example:
515
516 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 0
517
518 The correct way to do it:
519
520 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 1
521
522 To remove the default connection, which may have been created with a
523 call to addDatabase() not specifying a connection name, you can
524 retrieve the default connection name by calling connectionName() on
525 the database returned by database(). Note that if a default database
526 hasn't been created an invalid database will be returned.
527
528 \sa database() connectionName() {Threads and the SQL Module}
529*/
530
531void QSqlDatabase::removeDatabase(const QString& connectionName)
532{
533 QSqlDatabasePrivate::removeDatabase(connectionName);
534}
535
536/*!
537 Returns a list of all the available database drivers.
538
539 \sa registerSqlDriver()
540*/
541
542QStringList QSqlDatabase::drivers()
543{
544 QStringList list;
545
546#ifdef QT_SQL_PSQL
547 list << QLatin1String("QPSQL7");
548 list << QLatin1String("QPSQL");
549#endif
550#ifdef QT_SQL_MYSQL
551 list << QLatin1String("QMYSQL3");
552 list << QLatin1String("QMYSQL");
553#endif
554#ifdef QT_SQL_ODBC
555 list << QLatin1String("QODBC3");
556 list << QLatin1String("QODBC");
557#endif
558#ifdef QT_SQL_OCI
559 list << QLatin1String("QOCI8");
560 list << QLatin1String("QOCI");
561#endif
562#ifdef QT_SQL_TDS
563 list << QLatin1String("QTDS7");
564 list << QLatin1String("QTDS");
565#endif
566#ifdef QT_SQL_DB2
567 list << QLatin1String("QDB2");
568#endif
569#ifdef QT_SQL_SQLITE
570 list << QLatin1String("QSQLITE");
571#endif
572#ifdef QT_SQL_SQLITE2
573 list << QLatin1String("QSQLITE2");
574#endif
575#ifdef QT_SQL_IBASE
576 list << QLatin1String("QIBASE");
577#endif
578
579#if !defined(QT_NO_LIBRARY) && !defined(QT_NO_SETTINGS)
580 if (QFactoryLoader *fl = loader()) {
581 QStringList keys = fl->keys();
582 for (QStringList::const_iterator i = keys.constBegin(); i != keys.constEnd(); ++i) {
583 if (!list.contains(*i))
584 list << *i;
585 }
586 }
587#endif
588
589 DriverDict dict = QSqlDatabasePrivate::driverDict();
590 for (DriverDict::const_iterator i = dict.constBegin(); i != dict.constEnd(); ++i) {
591 if (!list.contains(i.key()))
592 list << i.key();
593 }
594
595 return list;
596}
597
598/*!
599 This function registers a new SQL driver called \a name, within
600 the SQL framework. This is useful if you have a custom SQL driver
601 and don't want to compile it as a plugin.
602
603 Example:
604 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 2
605
606 QSqlDatabase takes ownership of the \a creator pointer, so you
607 mustn't delete it yourself.
608
609 \sa drivers()
610*/
611void QSqlDatabase::registerSqlDriver(const QString& name, QSqlDriverCreatorBase *creator)
612{
613 delete QSqlDatabasePrivate::driverDict().take(name);
614 if (creator)
615 QSqlDatabasePrivate::driverDict().insert(name, creator);
616}
617
618/*!
619 \threadsafe
620
621 Returns true if the list of database connections contains \a
622 connectionName; otherwise returns false.
623
624 \sa connectionNames(), database(), {Threads and the SQL Module}
625*/
626
627bool QSqlDatabase::contains(const QString& connectionName)
628{
629 return dbDict()->contains_ts(connectionName);
630}
631
632/*!
633 \threadsafe
634
635 Returns a list containing the names of all connections.
636
637 \sa contains(), database(), {Threads and the SQL Module}
638*/
639QStringList QSqlDatabase::connectionNames()
640{
641 return dbDict()->keys_ts();
642}
643
644/*!
645 \overload
646
647 Creates a QSqlDatabase connection that uses the driver referred
648 to by \a type. If the \a type is not recognized, the database
649 connection will have no functionality.
650
651 The currently available driver types are:
652
653 \table
654 \header \i Driver Type \i Description
655 \row \i QDB2 \i IBM DB2
656 \row \i QIBASE \i Borland InterBase Driver
657 \row \i QMYSQL \i MySQL Driver
658 \row \i QOCI \i Oracle Call Interface Driver
659 \row \i QODBC \i ODBC Driver (includes Microsoft SQL Server)
660 \row \i QPSQL \i PostgreSQL Driver
661 \row \i QSQLITE \i SQLite version 3 or above
662 \row \i QSQLITE2 \i SQLite version 2
663 \row \i QTDS \i Sybase Adaptive Server
664 \endtable
665
666 Additional third party drivers, including your own custom
667 drivers, can be loaded dynamically.
668
669 \sa {SQL Database Drivers}, registerSqlDriver(), drivers()
670*/
671
672QSqlDatabase::QSqlDatabase(const QString &type)
673{
674 d = new QSqlDatabasePrivate(this);
675 d->init(type);
676}
677
678/*!
679 \overload
680
681 Creates a database connection using the given \a driver.
682*/
683
684QSqlDatabase::QSqlDatabase(QSqlDriver *driver)
685{
686 d = new QSqlDatabasePrivate(this, driver);
687}
688
689/*!
690 Creates an empty, invalid QSqlDatabase object. Use addDatabase(),
691 removeDatabase(), and database() to get valid QSqlDatabase
692 objects.
693*/
694QSqlDatabase::QSqlDatabase()
695{
696 d = QSqlDatabasePrivate::shared_null();
697 d->ref.ref();
698}
699
700/*!
701 Creates a copy of \a other.
702*/
703QSqlDatabase::QSqlDatabase(const QSqlDatabase &other)
704{
705 d = other.d;
706 d->ref.ref();
707}
708
709/*!
710 Assigns \a other to this object.
711*/
712QSqlDatabase &QSqlDatabase::operator=(const QSqlDatabase &other)
713{
714 qAtomicAssign(d, other.d);
715 return *this;
716}
717
718/*!
719 \internal
720
721 Create the actual driver instance \a type.
722*/
723
724void QSqlDatabasePrivate::init(const QString &type)
725{
726 drvName = type;
727
728 if (!driver) {
729#ifdef QT_SQL_PSQL
730 if (type == QLatin1String("QPSQL") || type == QLatin1String("QPSQL7"))
731 driver = new QPSQLDriver();
732#endif
733#ifdef QT_SQL_MYSQL
734 if (type == QLatin1String("QMYSQL") || type == QLatin1String("QMYSQL3"))
735 driver = new QMYSQLDriver();
736#endif
737#ifdef QT_SQL_ODBC
738 if (type == QLatin1String("QODBC") || type == QLatin1String("QODBC3"))
739 driver = new QODBCDriver();
740#endif
741#ifdef QT_SQL_OCI
742 if (type == QLatin1String("QOCI") || type == QLatin1String("QOCI8"))
743 driver = new QOCIDriver();
744#endif
745#ifdef QT_SQL_TDS
746 if (type == QLatin1String("QTDS") || type == QLatin1String("QTDS7"))
747 driver = new QTDSDriver();
748#endif
749#ifdef QT_SQL_DB2
750 if (type == QLatin1String("QDB2"))
751 driver = new QDB2Driver();
752#endif
753#ifdef QT_SQL_SQLITE
754 if (type == QLatin1String("QSQLITE"))
755 driver = new QSQLiteDriver();
756#endif
757#ifdef QT_SQL_SQLITE2
758 if (type == QLatin1String("QSQLITE2"))
759 driver = new QSQLite2Driver();
760#endif
761#ifdef QT_SQL_IBASE
762 if (type == QLatin1String("QIBASE"))
763 driver = new QIBaseDriver();
764#endif
765 }
766
767 if (!driver) {
768 DriverDict dict = QSqlDatabasePrivate::driverDict();
769 for (DriverDict::const_iterator it = dict.constBegin();
770 it != dict.constEnd() && !driver; ++it) {
771 if (type == it.key()) {
772 driver = ((QSqlDriverCreatorBase*)(*it))->createObject();
773 }
774 }
775 }
776
777#if !defined(QT_NO_LIBRARY) && !defined(QT_NO_SETTINGS)
778 if (!driver && loader()) {
779 if (QSqlDriverFactoryInterface *factory = qobject_cast<QSqlDriverFactoryInterface*>(loader()->instance(type)))
780 driver = factory->create(type);
781 }
782#endif // QT_NO_LIBRARY
783
784 if (!driver) {
785 qWarning("QSqlDatabase: %s driver not loaded", type.toLatin1().data());
786 qWarning("QSqlDatabase: available drivers: %s",
787 QSqlDatabase::drivers().join(QLatin1String(" ")).toLatin1().data());
788 if (QCoreApplication::instance() == 0)
789 qWarning("QSqlDatabase: an instance of QCoreApplication is required for loading driver plugins");
790 driver = shared_null()->driver;
791 }
792}
793
794/*!
795 Destroys the object and frees any allocated resources.
796
797 If this is the last QSqlDatabase object that uses a certain
798 database connection, the is automatically closed.
799
800 \sa close()
801*/
802
803QSqlDatabase::~QSqlDatabase()
804{
805 if (!d->ref.deref()) {
806 close();
807 delete d;
808 }
809}
810
811/*!
812 Executes a SQL statement on the database and returns a QSqlQuery
813 object. Use lastError() to retrieve error information. If \a
814 query is empty, an empty, invalid query is returned and
815 lastError() is not affected.
816
817 \sa QSqlQuery, lastError()
818*/
819
820QSqlQuery QSqlDatabase::exec(const QString & query) const
821{
822 QSqlQuery r(d->driver->createResult());
823 if (!query.isEmpty()) {
824 r.exec(query);
825 d->driver->setLastError(r.lastError());
826 }
827 return r;
828}
829
830/*!
831 Opens the database connection using the current connection
832 values. Returns true on success; otherwise returns false. Error
833 information can be retrieved using lastError().
834
835 \sa lastError() setDatabaseName() setUserName() setPassword()
836 \sa setHostName() setPort() setConnectOptions()
837*/
838
839bool QSqlDatabase::open()
840{
841 return d->driver->open(d->dbname, d->uname, d->pword, d->hname,
842 d->port, d->connOptions);
843}
844
845/*!
846 \overload
847
848 Opens the database connection using the given \a user name and \a
849 password. Returns true on success; otherwise returns false. Error
850 information can be retrieved using the lastError() function.
851
852 This function does not store the password it is given. Instead,
853 the password is passed directly to the driver for opening the
854 connection and it is then discarded.
855
856 \sa lastError()
857*/
858
859bool QSqlDatabase::open(const QString& user, const QString& password)
860{
861 setUserName(user);
862 return d->driver->open(d->dbname, user, password, d->hname,
863 d->port, d->connOptions);
864}
865
866/*!
867 Closes the database connection, freeing any resources acquired, and
868 invalidating any existing QSqlQuery objects that are used with the
869 database.
870
871 This will also affect copies of this QSqlDatabase object.
872
873 \sa removeDatabase()
874*/
875
876void QSqlDatabase::close()
877{
878 d->driver->close();
879}
880
881/*!
882 Returns true if the database connection is currently open;
883 otherwise returns false.
884*/
885
886bool QSqlDatabase::isOpen() const
887{
888 return d->driver->isOpen();
889}
890
891/*!
892 Returns true if there was an error opening the database
893 connection; otherwise returns false. Error information can be
894 retrieved using the lastError() function.
895*/
896
897bool QSqlDatabase::isOpenError() const
898{
899 return d->driver->isOpenError();
900}
901
902/*!
903 Begins a transaction on the database if the driver supports
904 transactions. Returns \c{true} if the operation succeeded.
905 Otherwise it returns \c{false}.
906
907 \sa QSqlDriver::hasFeature(), commit(), rollback()
908*/
909bool QSqlDatabase::transaction()
910{
911 if (!d->driver->hasFeature(QSqlDriver::Transactions))
912 return false;
913 return d->driver->beginTransaction();
914}
915
916/*!
917 Commits a transaction to the database if the driver supports
918 transactions and a transaction() has been started. Returns \c{true}
919 if the operation succeeded. Otherwise it returns \c{false}.
920
921 \note For some databases, the commit will fail and return \c{false}
922 if there is an \l{QSqlQuery::isActive()} {active query} using the
923 database for a \c{SELECT}. Make the query \l{QSqlQuery::isActive()}
924 {inactive} before doing the commit.
925
926 Call lastError() to get information about errors.
927
928 \sa QSqlQuery::isActive() QSqlDriver::hasFeature() rollback()
929*/
930bool QSqlDatabase::commit()
931{
932 if (!d->driver->hasFeature(QSqlDriver::Transactions))
933 return false;
934 return d->driver->commitTransaction();
935}
936
937/*!
938 Rolls back a transaction on the database, if the driver supports
939 transactions and a transaction() has been started. Returns \c{true}
940 if the operation succeeded. Otherwise it returns \c{false}.
941
942 \note For some databases, the rollback will fail and return
943 \c{false} if there is an \l{QSqlQuery::isActive()} {active query}
944 using the database for a \c{SELECT}. Make the query
945 \l{QSqlQuery::isActive()} {inactive} before doing the rollback.
946
947 Call lastError() to get information about errors.
948
949 \sa QSqlQuery::isActive() QSqlDriver::hasFeature() commit()
950*/
951bool QSqlDatabase::rollback()
952{
953 if (!d->driver->hasFeature(QSqlDriver::Transactions))
954 return false;
955 return d->driver->rollbackTransaction();
956}
957
958/*!
959 Sets the connection's database name to \a name. To have effect,
960 the database name must be set \e{before} the connection is
961 \l{open()} {opened}. Alternatively, you can close() the
962 connection, set the database name, and call open() again. \note
963 The \e{database name} is not the \e{connection name}. The
964 connection name must be passed to addDatabase() at connection
965 object create time.
966
967 For the QOCI (Oracle) driver, the database name is the TNS
968 Service Name.
969
970 For the QODBC driver, the \a name can either be a DSN, a DSN
971 filename (in which case the file must have a \c .dsn extension),
972 or a connection string.
973
974 For example, Microsoft Access users can use the following
975 connection string to open an \c .mdb file directly, instead of
976 having to create a DSN entry in the ODBC manager:
977
978 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 3
979
980 There is no default value.
981
982 \sa databaseName() setUserName() setPassword() setHostName()
983 \sa setPort() setConnectOptions() open()
984*/
985
986void QSqlDatabase::setDatabaseName(const QString& name)
987{
988 if (isValid())
989 d->dbname = name;
990}
991
992/*!
993 Sets the connection's user name to \a name. To have effect, the
994 user name must be set \e{before} the connection is \l{open()}
995 {opened}. Alternatively, you can close() the connection, set the
996 user name, and call open() again.
997
998 There is no default value.
999
1000 \sa userName() setDatabaseName() setPassword() setHostName()
1001 \sa setPort() setConnectOptions() open()
1002*/
1003
1004void QSqlDatabase::setUserName(const QString& name)
1005{
1006 if (isValid())
1007 d->uname = name;
1008}
1009
1010/*!
1011 Sets the connection's password to \a password. To have effect, the
1012 password must be set \e{before} the connection is \l{open()}
1013 {opened}. Alternatively, you can close() the connection, set the
1014 password, and call open() again.
1015
1016 There is no default value.
1017
1018 \warning This function stores the password in plain text within
1019 Qt. Use the open() call that takes a password as parameter to
1020 avoid this behavior.
1021
1022 \sa password() setUserName() setDatabaseName() setHostName()
1023 \sa setPort() setConnectOptions() open()
1024*/
1025
1026void QSqlDatabase::setPassword(const QString& password)
1027{
1028 if (isValid())
1029 d->pword = password;
1030}
1031
1032/*!
1033 Sets the connection's host name to \a host. To have effect, the
1034 host name must be set \e{before} the connection is \l{open()}
1035 {opened}. Alternatively, you can close() the connection, set the
1036 host name, and call open() again.
1037
1038 There is no default value.
1039
1040 \sa hostName() setUserName() setPassword() setDatabaseName()
1041 \sa setPort() setConnectOptions() open()
1042*/
1043
1044void QSqlDatabase::setHostName(const QString& host)
1045{
1046 if (isValid())
1047 d->hname = host;
1048}
1049
1050/*!
1051 Sets the connection's port number to \a port. To have effect, the
1052 port number must be set \e{before} the connection is \l{open()}
1053 {opened}. Alternatively, you can close() the connection, set the
1054 port number, and call open() again..
1055
1056 There is no default value.
1057
1058 \sa port() setUserName() setPassword() setHostName()
1059 \sa setDatabaseName() setConnectOptions() open()
1060*/
1061
1062void QSqlDatabase::setPort(int port)
1063{
1064 if (isValid())
1065 d->port = port;
1066}
1067
1068/*!
1069 Returns the connection's database name, which may be empty.
1070 \note The database name is not the connection name.
1071
1072 \sa setDatabaseName()
1073*/
1074QString QSqlDatabase::databaseName() const
1075{
1076 return d->dbname;
1077}
1078
1079/*!
1080 Returns the connection's user name; it may be empty.
1081
1082 \sa setUserName()
1083*/
1084QString QSqlDatabase::userName() const
1085{
1086 return d->uname;
1087}
1088
1089/*!
1090 Returns the connection's password. If the password was not set
1091 with setPassword(), and if the password was given in the open()
1092 call, or if no password was used, an empty string is returned.
1093*/
1094QString QSqlDatabase::password() const
1095{
1096 return d->pword;
1097}
1098
1099/*!
1100 Returns the connection's host name; it may be empty.
1101
1102 \sa setHostName()
1103*/
1104QString QSqlDatabase::hostName() const
1105{
1106 return d->hname;
1107}
1108
1109/*!
1110 Returns the connection's driver name.
1111
1112 \sa addDatabase(), driver()
1113*/
1114QString QSqlDatabase::driverName() const
1115{
1116 return d->drvName;
1117}
1118
1119/*!
1120 Returns the connection's port number. The value is undefined if
1121 the port number has not been set.
1122
1123 \sa setPort()
1124*/
1125int QSqlDatabase::port() const
1126{
1127 return d->port;
1128}
1129
1130/*!
1131 Returns the database driver used to access the database
1132 connection.
1133
1134 \sa addDatabase() drivers()
1135*/
1136
1137QSqlDriver* QSqlDatabase::driver() const
1138{
1139 return d->driver;
1140}
1141
1142/*!
1143 Returns information about the last error that occurred on the
1144 database.
1145
1146 Failures that occur in conjunction with an individual query are
1147 reported by QSqlQuery::lastError().
1148
1149 \sa QSqlError, QSqlQuery::lastError()
1150*/
1151
1152QSqlError QSqlDatabase::lastError() const
1153{
1154 return d->driver->lastError();
1155}
1156
1157
1158/*!
1159 Returns a list of the database's tables, system tables and views,
1160 as specified by the parameter \a type.
1161
1162 \sa primaryIndex(), record()
1163*/
1164
1165QStringList QSqlDatabase::tables(QSql::TableType type) const
1166{
1167 return d->driver->tables(type);
1168}
1169
1170/*!
1171 Returns the primary index for table \a tablename. If no primary
1172 index exists an empty QSqlIndex is returned.
1173
1174 \sa tables(), record()
1175*/
1176
1177QSqlIndex QSqlDatabase::primaryIndex(const QString& tablename) const
1178{
1179 return d->driver->primaryIndex(tablename);
1180}
1181
1182
1183/*!
1184 Returns a QSqlRecord populated with the names of all the fields in
1185 the table (or view) called \a tablename. The order in which the
1186 fields appear in the record is undefined. If no such table (or
1187 view) exists, an empty record is returned.
1188*/
1189
1190QSqlRecord QSqlDatabase::record(const QString& tablename) const
1191{
1192 return d->driver->record(tablename);
1193}
1194
1195
1196/*!
1197 Sets database-specific \a options. This must be done before the
1198 connection is opened or it has no effect (or you can close() the
1199 connection, call this function and open() the connection again).
1200
1201 The format of the \a options string is a semicolon separated list
1202 of option names or option=value pairs. The options depend on the
1203 database client used:
1204
1205 \table
1206 \header \i ODBC \i MySQL \i PostgreSQL
1207 \row
1208
1209 \i
1210 \list
1211 \i SQL_ATTR_ACCESS_MODE
1212 \i SQL_ATTR_LOGIN_TIMEOUT
1213 \i SQL_ATTR_CONNECTION_TIMEOUT
1214 \i SQL_ATTR_CURRENT_CATALOG
1215 \i SQL_ATTR_METADATA_ID
1216 \i SQL_ATTR_PACKET_SIZE
1217 \i SQL_ATTR_TRACEFILE
1218 \i SQL_ATTR_TRACE
1219 \i SQL_ATTR_CONNECTION_POOLING
1220 \i SQL_ATTR_ODBC_VERSION
1221 \endlist
1222
1223 \i
1224 \list
1225 \i CLIENT_COMPRESS
1226 \i CLIENT_FOUND_ROWS
1227 \i CLIENT_IGNORE_SPACE
1228 \i CLIENT_SSL
1229 \i CLIENT_ODBC
1230 \i CLIENT_NO_SCHEMA
1231 \i CLIENT_INTERACTIVE
1232 \i UNIX_SOCKET
1233 \i MYSQL_OPT_RECONNECT
1234 \endlist
1235
1236 \i
1237 \list
1238 \i connect_timeout
1239 \i options
1240 \i tty
1241 \i requiressl
1242 \i service
1243 \endlist
1244
1245 \header \i DB2 \i OCI \i TDS
1246 \row
1247
1248 \i
1249 \list
1250 \i SQL_ATTR_ACCESS_MODE
1251 \i SQL_ATTR_LOGIN_TIMEOUT
1252 \endlist
1253
1254 \i
1255 \list
1256 \i OCI_ATTR_PREFETCH_ROWS
1257 \i OCI_ATTR_PREFETCH_MEMORY
1258 \endlist
1259
1260 \i
1261 \e none
1262
1263 \header \i SQLite \i Interbase
1264 \row
1265
1266 \i
1267 \list
1268 \i QSQLITE_BUSY_TIMEOUT
1269 \i QSQLITE_OPEN_READONLY
1270 \i QSQLITE_ENABLE_SHARED_CACHE
1271 \endlist
1272
1273 \i
1274 \list
1275 \i ISC_DPB_LC_CTYPE
1276 \i ISC_DPB_SQL_ROLE_NAME
1277 \endlist
1278
1279 \endtable
1280
1281 Examples:
1282 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 4
1283
1284 Refer to the client library documentation for more information
1285 about the different options.
1286
1287 \sa connectOptions()
1288*/
1289
1290void QSqlDatabase::setConnectOptions(const QString &options)
1291{
1292 if (isValid())
1293 d->connOptions = options;
1294}
1295
1296/*!
1297 Returns the connection options string used for this connection.
1298 The string may be empty.
1299
1300 \sa setConnectOptions()
1301 */
1302QString QSqlDatabase::connectOptions() const
1303{
1304 return d->connOptions;
1305}
1306
1307/*!
1308 Returns true if a driver called \a name is available; otherwise
1309 returns false.
1310
1311 \sa drivers()
1312*/
1313
1314bool QSqlDatabase::isDriverAvailable(const QString& name)
1315{
1316 return drivers().contains(name);
1317}
1318
1319/*! \fn QSqlDatabase QSqlDatabase::addDatabase(QSqlDriver* driver, const QString& connectionName)
1320
1321 This overload is useful when you want to create a database
1322 connection with a \l{QSqlDriver} {driver} you instantiated
1323 yourself. It might be your own database driver, or you might just
1324 need to instantiate one of the Qt drivers yourself. If you do
1325 this, it is recommended that you include the driver code in your
1326 application. For example, you can create a PostgreSQL connection
1327 with your own QPSQL driver like this:
1328
1329 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 5
1330 \codeline
1331 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 6
1332
1333 The above code sets up a PostgreSQL connection and instantiates a
1334 QPSQLDriver object. Next, addDatabase() is called to add the
1335 connection to the known connections so that it can be used by the
1336 Qt SQL classes. When a driver is instantiated with a connection
1337 handle (or set of handles), Qt assumes that you have already
1338 opened the database connection.
1339
1340 \note We assume that \c qtdir is the directory where Qt is
1341 installed. This will pull in the code that is needed to use the
1342 PostgreSQL client library and to instantiate a QPSQLDriver object,
1343 assuming that you have the PostgreSQL headers somewhere in your
1344 include search path.
1345
1346 Remember that you must link your application against the database
1347 client library. Make sure the client library is in your linker's
1348 search path, and add lines like these to your \c{.pro} file:
1349
1350 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 7
1351
1352 The method described works for all the supplied drivers. The only
1353 difference will be in the driver constructor arguments. Here is a
1354 table of the drivers included with Qt, their source code files,
1355 and their constructor arguments:
1356
1357 \table
1358 \header \i Driver \i Class name \i Constructor arguments \i File to include
1359 \row
1360 \i QPSQL
1361 \i QPSQLDriver
1362 \i PGconn *connection
1363 \i \c qsql_psql.cpp
1364 \row
1365 \i QMYSQL
1366 \i QMYSQLDriver
1367 \i MYSQL *connection
1368 \i \c qsql_mysql.cpp
1369 \row
1370 \i QOCI
1371 \i QOCIDriver
1372 \i OCIEnv *environment, OCISvcCtx *serviceContext
1373 \i \c qsql_oci.cpp
1374 \row
1375 \i QODBC
1376 \i QODBCDriver
1377 \i SQLHANDLE environment, SQLHANDLE connection
1378 \i \c qsql_odbc.cpp
1379 \row
1380 \i QDB2
1381 \i QDB2
1382 \i SQLHANDLE environment, SQLHANDLE connection
1383 \i \c qsql_db2.cpp
1384 \row
1385 \i QTDS
1386 \i QTDSDriver
1387 \i LOGINREC *loginRecord, DBPROCESS *dbProcess, const QString &hostName
1388 \i \c qsql_tds.cpp
1389 \row
1390 \i QSQLITE
1391 \i QSQLiteDriver
1392 \i sqlite *connection
1393 \i \c qsql_sqlite.cpp
1394 \row
1395 \i QIBASE
1396 \i QIBaseDriver
1397 \i isc_db_handle connection
1398 \i \c qsql_ibase.cpp
1399 \endtable
1400
1401 The host name (or service name) is needed when constructing the
1402 QTDSDriver for creating new connections for internal queries. This
1403 is to prevent blocking when several QSqlQuery objects are used
1404 simultaneously.
1405
1406 \warning Adding a database connection with the same connection
1407 name as an existing connection, causes the existing connection to
1408 be replaced by the new one.
1409
1410 \warning The SQL framework takes ownership of the \a driver. It
1411 must not be deleted. To remove the connection, use
1412 removeDatabase().
1413
1414 \sa drivers()
1415*/
1416QSqlDatabase QSqlDatabase::addDatabase(QSqlDriver* driver, const QString& connectionName)
1417{
1418 QSqlDatabase db(driver);
1419 QSqlDatabasePrivate::addDatabase(db, connectionName);
1420 return db;
1421}
1422
1423/*!
1424 Returns true if the QSqlDatabase has a valid driver.
1425
1426 Example:
1427 \snippet doc/src/snippets/code/src_sql_kernel_qsqldatabase.cpp 8
1428*/
1429bool QSqlDatabase::isValid() const
1430{
1431 return d->driver && d->driver != d->shared_null()->driver;
1432}
1433
1434#ifdef QT3_SUPPORT
1435/*!
1436 Use query.record() instead.
1437*/
1438QSqlRecord QSqlDatabase::record(const QSqlQuery& query) const
1439{ return query.record(); }
1440
1441/*!
1442 Use query.record() instead.
1443*/
1444QSqlRecord QSqlDatabase::recordInfo(const QSqlQuery& query) const
1445{ return query.record(); }
1446
1447/*!
1448 \fn QSqlRecord QSqlDatabase::recordInfo(const QString& tablename) const
1449
1450 Use record() instead.
1451*/
1452#endif
1453
1454/*!
1455 Clones the database connection \a other and and stores it as \a
1456 connectionName. All the settings from the original database, e.g.
1457 databaseName(), hostName(), etc., are copied across. Does nothing
1458 if \a other is an invalid database. Returns the newly created
1459 database connection.
1460
1461 \note The new connection has not been opened. Before using the new
1462 connection, you must call open().
1463*/
1464QSqlDatabase QSqlDatabase::cloneDatabase(const QSqlDatabase &other, const QString &connectionName)
1465{
1466 if (!other.isValid())
1467 return QSqlDatabase();
1468
1469 QSqlDatabase db(other.driverName());
1470 db.d->copy(other.d);
1471 QSqlDatabasePrivate::addDatabase(db, connectionName);
1472 return db;
1473}
1474
1475/*!
1476 \since 4.4
1477
1478 Returns the connection name, which may be empty. \note The
1479 connection name is not the \l{databaseName()} {database name}.
1480
1481 \sa addDatabase()
1482*/
1483QString QSqlDatabase::connectionName() const
1484{
1485 return d->connName;
1486}
1487
1488/*!
1489 \since 4.6
1490
1491 Sets the default numerical precision policy used by queries created
1492 on this database connection to \a precisionPolicy.
1493
1494 Note: Drivers that don't support fetching numerical values with low
1495 precision will ignore the precision policy. You can use
1496 QSqlDriver::hasFeature() to find out whether a driver supports this
1497 feature.
1498
1499 Note: Setting the default precision policy to \a precisionPolicy
1500 doesn't affect any currently active queries.
1501
1502 \sa QSql::NumericalPrecisionPolicy, numericalPrecisionPolicy(),
1503 QSqlQuery::setNumericalPrecisionPolicy(), QSqlQuery::numericalPrecisionPolicy()
1504*/
1505void QSqlDatabase::setNumericalPrecisionPolicy(QSql::NumericalPrecisionPolicy precisionPolicy)
1506{
1507 if(driver())
1508 driver()->setNumericalPrecisionPolicy(precisionPolicy);
1509 d->precisionPolicy = precisionPolicy;
1510}
1511
1512/*!
1513 \since 4.6
1514
1515 Returns the current default precision policy for the database connection.
1516
1517 \sa QSql::NumericalPrecisionPolicy, setNumericalPrecisionPolicy(),
1518 QSqlQuery::numericalPrecisionPolicy(), QSqlQuery::setNumericalPrecisionPolicy()
1519*/
1520QSql::NumericalPrecisionPolicy QSqlDatabase::numericalPrecisionPolicy() const
1521{
1522 if(driver())
1523 return driver()->numericalPrecisionPolicy();
1524 else
1525 return d->precisionPolicy;
1526}
1527
1528
1529#ifndef QT_NO_DEBUG_STREAM
1530QDebug operator<<(QDebug dbg, const QSqlDatabase &d)
1531{
1532 if (!d.isValid()) {
1533 dbg.nospace() << "QSqlDatabase(invalid)";
1534 return dbg.space();
1535 }
1536
1537 dbg.nospace() << "QSqlDatabase(driver=\"" << d.driverName() << "\", database=\""
1538 << d.databaseName() << "\", host=\"" << d.hostName() << "\", port=" << d.port()
1539 << ", user=\"" << d.userName() << "\", open=" << d.isOpen() << ")";
1540 return dbg.space();
1541}
1542#endif
1543
1544QT_END_NAMESPACE
Note: See TracBrowser for help on using the repository browser.