aboutsummaryrefslogtreecommitdiffstats
path: root/SQLiteStudio3
diff options
context:
space:
mode:
authorLibravatarUnit 193 <unit193@unit193.net>2025-01-16 01:58:22 -0500
committerLibravatarUnit 193 <unit193@unit193.net>2025-01-16 01:58:22 -0500
commita5ae79be08125b31bb6b8d9703090a98c6fd2e30 (patch)
tree569ee612c9de85b2bb423efa485688ef1d43852e /SQLiteStudio3
parent21966b4f924b0a1933d9662e75ff253bd154fdb7 (diff)
parent81a21e6ce040e7740de86340c8ea4dba30e69bc3 (diff)
Update upstream source from tag 'upstream/3.4.13+dfsg'
Update to upstream version '3.4.13+dfsg' with Debian dir bf81ee0219cb8e4562a4751df17d75814772d2d6
Diffstat (limited to 'SQLiteStudio3')
-rw-r--r--SQLiteStudio3/SQLiteStudio3.pro2
-rw-r--r--SQLiteStudio3/Tests/ParserTest/tst_parsertest.cpp15
-rw-r--r--SQLiteStudio3/Tests/TableModifierTest/tst_tablemodifiertest.cpp2
-rw-r--r--SQLiteStudio3/Tests/TestUtils/collationmanagermock.cpp5
-rw-r--r--SQLiteStudio3/Tests/TestUtils/collationmanagermock.h1
-rw-r--r--SQLiteStudio3/Tests/TestUtils/dbmanagermock.cpp5
-rw-r--r--SQLiteStudio3/Tests/TestUtils/dbmanagermock.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/common/utils_sql.cpp62
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/common/utils_sql.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/completioncomparer.cpp20
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/completioncomparer.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/completionhelper.cpp38
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/completionhelper.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/coreSQLiteStudio.pro2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/abstractdb.cpp112
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/abstractdb.h9
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/abstractdb3.h30
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/db.h42
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.cpp15
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/invaliddb.cpp14
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/invaliddb.h7
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.cpp104
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.h34
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutoraddrowids.cpp9
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.cpp78
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorexecute.cpp2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorfilter.cpp17
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorlimit.cpp1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutororder.cpp6
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorreplaceviews.cpp17
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.cpp80
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.h28
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/sqlite3.h1908
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/sqlquery.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/db/stdsqlite3driver.h5
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.cpp35
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.h3
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/expectedtoken.h10
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/exportworker.cpp8
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/exportworker.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/importworker.cpp19
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/importworker.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.cpp35
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.h9
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.cpp55
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqliteexpr.cpp7
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.cpp14
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.h8
-rwxr-xr-xSQLiteStudio3/coreSQLiteStudio/parser/compile_lemon.sh6
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/parser.cpp3
-rwxr-xr-xSQLiteStudio3/coreSQLiteStudio/parser/run_lemon.sh2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.cpp5221
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.y27
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/plugins/scriptingsql.cpp26
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/schemaresolver.cpp398
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/schemaresolver.h34
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/selectresolver.cpp97
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/selectresolver.h4
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/collationmanager.h7
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/config.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/dbmanager.h8
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/exportmanager.cpp2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/exportmanager.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.cpp15
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.cpp11
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.cpp12
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/impl/functionmanagerimpl.cpp25
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/importmanager.cpp3
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/services/importmanager.h1
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.cpp43
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.h2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/sqlitestudio.cpp2
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/tablemodifier.cpp71
-rw-r--r--SQLiteStudio3/coreSQLiteStudio/tablemodifier.h4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.cpp59
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.h34
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/widgetcover.cpp11
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/widgetcover.h1
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.cpp5
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.h1
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/completer/completerwindow.cpp4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/configmapper.cpp1
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/columncollatepanel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/columndefaultpanel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/columngeneratedpanel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/columnprimarykeypanel.cpp4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/columnuniqueandnotnullpanel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.cpp10
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.h4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.cpp32
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.cpp33
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.h1
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqldatasourcequerymodel.cpp8
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.cpp33
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.h9
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.cpp112
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.h6
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.cpp14
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.h20
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.cpp57
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.h18
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.cpp4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.h1
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryview.cpp10
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqltablemodel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/datagrid/sqlviewmodel.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dataview.cpp16
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dataview.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.cpp15
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.h6
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.cpp224
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.h15
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.cpp43
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/configdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/constraintdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.cpp28
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.ui37
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/ddlpreviewdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/exportdialog.cpp4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/importdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/indexdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/populatedialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/searchtextdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/dialogs/triggerdialog.cpp2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/extendedpalette.cpp5
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/extendedpalette.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/guiSQLiteStudio.pro4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/sqleditor.cpp41
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/sqleditor.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/taskbar.cpp12
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/translations/guiSQLiteStudio_de_DE.ts4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/uiutils.cpp16
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/uiutils.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.cpp62
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.h3
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.ui27
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.cpp27
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.cpp11
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.cpp46
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.cpp55
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.h18
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/sqliteextensioneditor.cpp4
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.cpp31
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.h2
-rw-r--r--SQLiteStudio3/guiSQLiteStudio/windows/viewwindow.cpp6
157 files changed, 6572 insertions, 3652 deletions
diff --git a/SQLiteStudio3/SQLiteStudio3.pro b/SQLiteStudio3/SQLiteStudio3.pro
index 1fd7959..20691e7 100644
--- a/SQLiteStudio3/SQLiteStudio3.pro
+++ b/SQLiteStudio3/SQLiteStudio3.pro
@@ -4,7 +4,7 @@ REQ_QT_MAJOR = 5
REQ_QT_MINOR = 12
REQ_QT_PATCH = 0
-lessThan(QT_MAJOR_VERSION, $$REQ_QT_MAJOR)|lessThan(QT_MINOR_VERSION, $$REQ_QT_MINOR)|lessThan(QT_MINOR_VERSION, $$REQ_QT_PATCH) {
+!versionAtLeast(QT_VERSION, $${REQ_QT_MAJOR}.$${REQ_QT_MINOR}.$${REQ_QT_PATCH}) {
error($$sprintf("Required Qt version is at least %1.%2.%3. This Qt version is %4.%5.%6.", \
$$REQ_QT_MAJOR, $$REQ_QT_MINOR, $$REQ_QT_PATCH, \
$$QT_MAJOR_VERSION, $$QT_MINOR_VERSION, $$QT_PATCH_VERSION))
diff --git a/SQLiteStudio3/Tests/ParserTest/tst_parsertest.cpp b/SQLiteStudio3/Tests/ParserTest/tst_parsertest.cpp
index eec1e39..d936e2b 100644
--- a/SQLiteStudio3/Tests/ParserTest/tst_parsertest.cpp
+++ b/SQLiteStudio3/Tests/ParserTest/tst_parsertest.cpp
@@ -51,6 +51,7 @@ class ParserTest : public QObject
void testBigNum();
void testSelectWith();
void testInsertWithDoubleQuoteValues();
+ void testInsertIncompleteOnColumnName();
void testParseAndRebuildAlias();
void testRebuildTokensUpdate();
void testRebuildTokensInsertUpsert();
@@ -469,6 +470,18 @@ void ParserTest::testInsertWithDoubleQuoteValues()
QVERIFY(sql.replace(" ", "") == detokenized);
}
+void ParserTest::testInsertIncompleteOnColumnName()
+{
+ QString sql = "INSERT INTO tabName (";
+ bool res = parser3->parse(sql, true);
+ QVERIFY(res);
+ QVERIFY(parser3->getErrors().isEmpty());
+
+ const SqliteInsertPtr insert = parser3->getQueries().first().dynamicCast<SqliteInsert>();
+ QVERIFY(insert->table == "tabName");
+ QVERIFY(insert->columnNames.isEmpty());
+}
+
void ParserTest::testParseAndRebuildAlias()
{
QString sql = "SELECT x AS [\"abc\".\"def\"];";
@@ -569,7 +582,7 @@ void ParserTest::testWindowClause()
void ParserTest::testWindowKwAsColumn()
{
QString sql = "SELECT window FROM test_table;";
- parser3->setLemonDebug(true);
+ //parser3->setLemonDebug(true);
bool res = parser3->parse(sql);
QVERIFY(res);
QVERIFY(parser3->getErrors().isEmpty());
diff --git a/SQLiteStudio3/Tests/TableModifierTest/tst_tablemodifiertest.cpp b/SQLiteStudio3/Tests/TableModifierTest/tst_tablemodifiertest.cpp
index a5e0ad1..e631683 100644
--- a/SQLiteStudio3/Tests/TableModifierTest/tst_tablemodifiertest.cpp
+++ b/SQLiteStudio3/Tests/TableModifierTest/tst_tablemodifiertest.cpp
@@ -43,7 +43,7 @@ TableModifierTest::TableModifierTest()
void TableModifierTest::verifyRe(const QString& re, const QString& sql, Qt::CaseSensitivity cs)
{
QRegExp regExp(re, cs);
- QVERIFY2(regExp.exactMatch(sql), QString("Failed RegExp validation:\n%1\nfor SQL:\n%2").arg(re).arg(sql).toLatin1().data());
+ QVERIFY2(regExp.exactMatch(sql), QString("Failed RegExp validation:\n%1\nfor SQL:\n%2\n").arg(re, sql).toLatin1().data());
}
void TableModifierTest::testCase1()
diff --git a/SQLiteStudio3/Tests/TestUtils/collationmanagermock.cpp b/SQLiteStudio3/Tests/TestUtils/collationmanagermock.cpp
index 640a252..b9efa46 100644
--- a/SQLiteStudio3/Tests/TestUtils/collationmanagermock.cpp
+++ b/SQLiteStudio3/Tests/TestUtils/collationmanagermock.cpp
@@ -13,6 +13,11 @@ QList<CollationManager::CollationPtr> CollationManagerMock::getAllCollations() c
return QList<CollationManager::CollationPtr>();
}
+CollationManager::CollationPtr CollationManagerMock::getCollation(const QString&) const
+{
+ return nullptr;
+}
+
QList<CollationManager::CollationPtr> CollationManagerMock::getCollationsForDatabase(const QString&) const
{
return QList<CollationManager::CollationPtr>();
diff --git a/SQLiteStudio3/Tests/TestUtils/collationmanagermock.h b/SQLiteStudio3/Tests/TestUtils/collationmanagermock.h
index eb08b7b..0b273d9 100644
--- a/SQLiteStudio3/Tests/TestUtils/collationmanagermock.h
+++ b/SQLiteStudio3/Tests/TestUtils/collationmanagermock.h
@@ -13,6 +13,7 @@ class CollationManagerMock : public CollationManager
QList<CollationPtr> getCollationsForDatabase(const QString&) const;
int evaluate(const QString&, const QString&, const QString&);
int evaluateDefault(const QString&, const QString&);
+ CollationPtr getCollation(const QString &name) const;
};
#endif // COLLATIONMANAGERMOCK_H
diff --git a/SQLiteStudio3/Tests/TestUtils/dbmanagermock.cpp b/SQLiteStudio3/Tests/TestUtils/dbmanagermock.cpp
index 10caed4..1956c6b 100644
--- a/SQLiteStudio3/Tests/TestUtils/dbmanagermock.cpp
+++ b/SQLiteStudio3/Tests/TestUtils/dbmanagermock.cpp
@@ -47,6 +47,11 @@ QStringList DbManagerMock::getDbNames()
return QStringList();
}
+QStringList DbManagerMock::getValidDbNames()
+{
+ return QStringList();
+}
+
Db* DbManagerMock::getByName(const QString&, Qt::CaseSensitivity)
{
return nullptr;
diff --git a/SQLiteStudio3/Tests/TestUtils/dbmanagermock.h b/SQLiteStudio3/Tests/TestUtils/dbmanagermock.h
index ee69fa1..df39b65 100644
--- a/SQLiteStudio3/Tests/TestUtils/dbmanagermock.h
+++ b/SQLiteStudio3/Tests/TestUtils/dbmanagermock.h
@@ -16,6 +16,7 @@ class DbManagerMock : public DbManager
QList<Db*> getValidDbList();
QList<Db*> getConnectedDbList();
QStringList getDbNames();
+ QStringList getValidDbNames();
Db* getByName(const QString&, Qt::CaseSensitivity);
Db* getByPath(const QString&);
Db* createInMemDb(bool = false);
diff --git a/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.cpp b/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.cpp
index 0122352..4b54090 100644
--- a/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.cpp
@@ -14,6 +14,7 @@ QString invalidIdCharacters = "[](){}\"'@*.,+-=/#$%&|:; \t\n<>";
QHash<NameWrapper,QPair<QChar,QChar>> wrapperChars;
QHash<NameWrapper,QPair<QChar,bool>> wrapperEscapedEnding;
QList<NameWrapper> sqlite3Wrappers;
+QSet<QString> sqlite3ReservedLiterals = {"true", "false"}; // true/false as column names - #5065
void initUtilsSql()
{
@@ -58,9 +59,17 @@ bool doesObjectNeedWrapping(const QString& str)
if (str[0].isDigit())
return true;
+ if (isReservedLiteral(str))
+ return true;
+
return false;
}
+bool isReservedLiteral(const QString& str)
+{
+ return sqlite3ReservedLiterals.contains(str.toLower());
+}
+
bool doesObjectNeedWrapping(const QChar& c)
{
return invalidIdCharacters.indexOf(c) >= 0;
@@ -822,38 +831,35 @@ QStringList valueListToSqlList(const QVariantList& values)
{
QStringList argList;
for (const QVariant& value : values)
- {
- if (!value.isValid() || value.isNull())
- {
- argList << "NULL";
- continue;
- }
+ argList << valueToSqlLiteral(value);
- switch (value.userType())
- {
- case QVariant::Int:
- case QVariant::UInt:
- case QVariant::LongLong:
- case QVariant::ULongLong:
- argList << value.toString();
- break;
- case QVariant::Double:
- argList << doubleToString(value);
- break;
- case QVariant::Bool:
- argList << QString::number(value.toInt());
- break;
- case QVariant::ByteArray:
- argList << "X'" + value.toByteArray().toHex().toUpper() + "'";
- break;
- default:
- argList << wrapString(escapeString(value.toString()));
- break;
- }
- }
return argList;
}
+QString valueToSqlLiteral(const QVariant& value)
+{
+ if (!value.isValid() || value.isNull())
+ return "NULL";
+
+ switch (value.userType())
+ {
+ case QVariant::Int:
+ case QVariant::UInt:
+ case QVariant::LongLong:
+ case QVariant::ULongLong:
+ return value.toString();
+ case QVariant::Double:
+ return doubleToString(value);
+ case QVariant::Bool:
+ return QString::number(value.toInt());
+ case QVariant::ByteArray:
+ return "X'" + value.toByteArray().toHex().toUpper() + "'";
+ default:
+ break;
+ }
+ return wrapString(escapeString(value.toString()));
+}
+
QStringList wrapStrings(const QStringList& strList)
{
QStringList list;
diff --git a/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.h b/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.h
index 353faf3..0c201e3 100644
--- a/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.h
+++ b/SQLiteStudio3/coreSQLiteStudio/common/utils_sql.h
@@ -44,6 +44,7 @@ API_EXPORT bool doesObjectNeedWrapping(const QChar& c);
API_EXPORT bool isObjectWrapped(const QChar& c);
API_EXPORT bool doesStringNeedWrapping(const QString& str);
API_EXPORT bool isStringWrapped(const QString& str);
+API_EXPORT bool isReservedLiteral(const QString& str);
API_EXPORT QString wrapObjIfNeeded(const QString& obj, NameWrapper favWrapper = NameWrapper::null);
API_EXPORT QString wrapObjIfNeeded(const QString& obj, bool useDoubleQuoteForEmptyValue, NameWrapper favWrapper = NameWrapper::null);
API_EXPORT QString wrapObjName(const QString& obj, NameWrapper favWrapper = NameWrapper::null);
@@ -88,6 +89,7 @@ API_EXPORT QString commentAllSqlLines(const QString& sql);
API_EXPORT QString getBindTokenName(const TokenPtr& token);
API_EXPORT QueryAccessMode getQueryAccessMode(const QString& query, bool* isSelect = nullptr);
API_EXPORT QStringList valueListToSqlList(const QList<QVariant>& values);
+API_EXPORT QString valueToSqlLiteral(const QVariant& value);
API_EXPORT QString trimQueryEnd(const QString& query);
API_EXPORT QByteArray blobFromLiteral(const QString& value);
diff --git a/SQLiteStudio3/coreSQLiteStudio/completioncomparer.cpp b/SQLiteStudio3/coreSQLiteStudio/completioncomparer.cpp
index cd6e2a5..1ff79db 100644
--- a/SQLiteStudio3/coreSQLiteStudio/completioncomparer.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/completioncomparer.cpp
@@ -11,6 +11,9 @@ CompletionComparer::CompletionComparer(CompletionHelper *helper)
bool CompletionComparer::operator ()(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2)
{
+ if (token2->type == ExpectedToken::OTHER || token1->type == ExpectedToken::OTHER)
+ qDebug() << "";
+
if ((token1->priority > 0 || token2->priority > 0) && token1->priority != token2->priority)
return token1->priority > token2->priority;
@@ -116,6 +119,8 @@ bool CompletionComparer::compareColumns(const ExpectedTokenPtr& token1, const Ex
case CompletionHelper::Context::UPDATE_WHERE:
result = compareColumnsForUpdateCol(token1, token2, &ok);
break;
+ case CompletionHelper::Context::INSERT_COLUMNS:
+ result = compareColumnsForInsertCol(token1, token2, &ok);
case CompletionHelper::Context::DELETE_WHERE:
result = compareColumnsForDeleteCol(token1, token2, &ok);
break;
@@ -192,7 +197,7 @@ bool CompletionComparer::compareColumnsForUpdateCol(const ExpectedTokenPtr &toke
if (token1->contextInfo == token2->contextInfo)
return compareValues(token1->value, token2->value);
- return compareByContext(token1->contextInfo, token2->contextInfo, contextTables);
+ return compareByContext(token1->contextInfo, token2->contextInfo, contextTables, true);
}
bool CompletionComparer::compareColumnsForDeleteCol(const ExpectedTokenPtr &token1, const ExpectedTokenPtr &token2, bool *result)
@@ -201,7 +206,16 @@ bool CompletionComparer::compareColumnsForDeleteCol(const ExpectedTokenPtr &toke
if (token1->contextInfo == token2->contextInfo)
return compareValues(token1->value, token2->value);
- return compareByContext(token1->contextInfo, token2->contextInfo, contextTables);
+ return compareByContext(token1->contextInfo, token2->contextInfo, contextTables, true);
+}
+
+bool CompletionComparer::compareColumnsForInsertCol(const ExpectedTokenPtr &token1, const ExpectedTokenPtr &token2, bool *result)
+{
+ *result = true;
+ if (token1->contextInfo == token2->contextInfo)
+ return compareValues(token1->value, token2->value);
+
+ return compareByContext(token1->contextInfo, token2->contextInfo, contextTables, true);
}
bool CompletionComparer::compareColumnsForCreateTable(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result)
@@ -304,7 +318,7 @@ bool CompletionComparer::compareValues(const ExpectedTokenPtr &token1, const Exp
bool CompletionComparer::compareValues(const QString &token1, const QString &token2, bool handleSystemNames)
{
- //qDebug() << "comparing" << token1 << "and" << token2 << "=" << token1.compare(token2, Qt::CaseInsensitive);
+ // qDebug() << "comparing" << token1 << "and" << token2 << "=" << token1.compare(token2, Qt::CaseInsensitive);
if (handleSystemNames)
{
bool firstIsSystem = token1.toLower().startsWith("sqlite_");
diff --git a/SQLiteStudio3/coreSQLiteStudio/completioncomparer.h b/SQLiteStudio3/coreSQLiteStudio/completioncomparer.h
index 92401a3..de14ba5 100644
--- a/SQLiteStudio3/coreSQLiteStudio/completioncomparer.h
+++ b/SQLiteStudio3/coreSQLiteStudio/completioncomparer.h
@@ -45,6 +45,7 @@ class CompletionComparer
bool compareColumnsForSelectResCol(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
bool compareColumnsForUpdateCol(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
bool compareColumnsForDeleteCol(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
+ bool compareColumnsForInsertCol(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
bool compareColumnsForCreateTable(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
bool compareColumnsForReturning(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2, bool* result);
bool compareTables(const ExpectedTokenPtr& token1, const ExpectedTokenPtr& token2);
diff --git a/SQLiteStudio3/coreSQLiteStudio/completionhelper.cpp b/SQLiteStudio3/coreSQLiteStudio/completionhelper.cpp
index b38e42d..9d5640f 100644
--- a/SQLiteStudio3/coreSQLiteStudio/completionhelper.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/completionhelper.cpp
@@ -257,13 +257,13 @@ QList<ExpectedTokenPtr> CompletionHelper::getExpectedTokens(TokenPtr token)
results += getExpectedToken(ExpectedToken::OTHER, QString(), QString(), tr("Any word"));
break;
case Token::STRING:
- results += getExpectedToken(ExpectedToken::STRING);
+ results += getExpectedToken(ExpectedToken::STRING, "''", QString(), tr("String"));
break;
case Token::FLOAT:
- results += getExpectedToken(ExpectedToken::NUMBER);
+ results += getExpectedToken(ExpectedToken::NUMBER, QString(), QString(), tr("Number"));
break;
case Token::INTEGER:
- results += getExpectedToken(ExpectedToken::NUMBER);
+ results += getExpectedToken(ExpectedToken::NUMBER, QString(), QString(), tr("Number"));
break;
case Token::OPERATOR:
results += getExpectedToken(ExpectedToken::OPERATOR, token->value);
@@ -275,7 +275,7 @@ QList<ExpectedTokenPtr> CompletionHelper::getExpectedTokens(TokenPtr token)
results += getExpectedToken(ExpectedToken::OPERATOR, ")");
break;
case Token::BLOB:
- results += getExpectedToken(ExpectedToken::BLOB);
+ results += getExpectedToken(ExpectedToken::BLOB, "X''", QString(), tr("BLOB literal"));
break;
case Token::KEYWORD:
results += getExpectedToken(ExpectedToken::KEYWORD, token->value);
@@ -634,6 +634,9 @@ QList<ExpectedTokenPtr> CompletionHelper::getColumns(const QString &prefixTable)
label = prefixTable+" = "+table;
}
+ if (!dbName.isNull())
+ dbName = translateDatabase(dbName);
+
// CREATE TRIGGER has a special "old" and "new" keywords as aliases for deleted/inserted/updated rows.
// They should refer to a table that the trigger is created for.
QString tableLower = table;
@@ -1070,6 +1073,10 @@ void CompletionHelper::extractQueryAdditionalInfo()
{
context = Context::EXPR;
}
+ else if (isInInsertColumns())
+ {
+ context = Context::INSERT_COLUMNS;
+ }
else if (isInUpdateReturning())
{
context = Context::UPDATE_RETURNING;
@@ -1179,6 +1186,29 @@ bool CompletionHelper::isInInsertReturning()
return isIn(SqliteQueryType::Insert, "returning", "RETURNING");
}
+bool CompletionHelper::isInInsertColumns()
+{
+ if (isIn(SqliteQueryType::Insert, "idlist_opt", QString()))
+ return true;
+
+ if (!parsedQuery)
+ return false;
+
+ if (parsedQuery->queryType != SqliteQueryType::Insert)
+ return false;
+
+ if (parsedQuery->tokensMap.contains("rp_opt"))
+ {
+ TokenList rpTokens = parsedQuery->tokensMap["rp_opt"];
+ if (rpTokens.isEmpty())
+ return parsedQuery->tokensMap["LP"][0]->start <= cursorPosition;
+ else
+ return rpTokens[0]->start >= cursorPosition;
+ }
+
+ return false;
+}
+
bool CompletionHelper::isIn(SqliteQueryType queryType, const QString &tokenMapKey, const QString &prefixKeyword)
{
if (!parsedQuery)
diff --git a/SQLiteStudio3/coreSQLiteStudio/completionhelper.h b/SQLiteStudio3/coreSQLiteStudio/completionhelper.h
index 3cff8ec..6e661e9 100644
--- a/SQLiteStudio3/coreSQLiteStudio/completionhelper.h
+++ b/SQLiteStudio3/coreSQLiteStudio/completionhelper.h
@@ -65,6 +65,7 @@ class API_EXPORT CompletionHelper : public QObject
CREATE_TABLE,
CREATE_TRIGGER,
EXPR,
+ INSERT_COLUMNS,
INSERT_RETURNING,
UPDATE_RETURNING,
DELETE_RETURNING
@@ -142,6 +143,7 @@ class API_EXPORT CompletionHelper : public QObject
bool isInDeleteWhere();
bool isInCreateTable();
bool isInCreateTrigger();
+ bool isInInsertColumns();
bool isInUpdateReturning();
bool isInDeleteReturning();
bool isInInsertReturning();
diff --git a/SQLiteStudio3/coreSQLiteStudio/coreSQLiteStudio.pro b/SQLiteStudio3/coreSQLiteStudio/coreSQLiteStudio.pro
index ee78caa..75beb97 100644
--- a/SQLiteStudio3/coreSQLiteStudio/coreSQLiteStudio.pro
+++ b/SQLiteStudio3/coreSQLiteStudio/coreSQLiteStudio.pro
@@ -66,6 +66,7 @@ SOURCES += sqlitestudio.cpp \
common/compatibility.cpp \
db/queryexecutorsteps/queryexecutorcolumntype.cpp \
db/queryexecutorsteps/queryexecutorfilter.cpp \
+ db/queryexecutorsteps/queryexecutorsmarthints.cpp \
parser/ast/sqlitefilterover.cpp \
parser/ast/sqlitenulls.cpp \
parser/ast/sqlitewindowdefinition.cpp \
@@ -245,6 +246,7 @@ HEADERS += sqlitestudio.h\
coreSQLiteStudio_global.h \
db/queryexecutorsteps/queryexecutorcolumntype.h \
db/queryexecutorsteps/queryexecutorfilter.h \
+ db/queryexecutorsteps/queryexecutorsmarthints.h \
db/sqlite3.h \
parser/ast/sqlitefilterover.h \
parser/ast/sqlitenulls.h \
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.cpp b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.cpp
index b137c1f..199b11d 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.cpp
@@ -67,9 +67,10 @@ bool AbstractDb::openQuiet()
bool AbstractDb::closeQuiet()
{
- QWriteLocker locker(&dbOperLock);
QWriteLocker connectionLocker(&connectionStateLock);
interruptExecution();
+
+ QWriteLocker locker(&dbOperLock);
bool res = closeInternal();
clearAttaches();
registeredFunctions.clear();
@@ -509,6 +510,51 @@ bool AbstractDb::isCollationRegistered(const QString& name)
return registeredCollations.contains(name);
}
+bool AbstractDb::beginNoLock()
+{
+ if (!isOpenInternal())
+ return false;
+
+ SqlQueryPtr results = exec("BEGIN;", Flag::NO_LOCK);
+ if (results->isError())
+ {
+ qCritical() << "Error while starting a transaction: " << results->getErrorCode() << results->getErrorText();
+ return false;
+ }
+
+ return true;
+}
+
+bool AbstractDb::commitNoLock()
+{
+ if (!isOpenInternal())
+ return false;
+
+ SqlQueryPtr results = exec("COMMIT;", Flag::NO_LOCK);
+ if (results->isError())
+ {
+ qCritical() << "Error while committing a transaction: " << results->getErrorCode() << results->getErrorText();
+ return false;
+ }
+
+ return true;
+}
+
+bool AbstractDb::rollbackNoLock()
+{
+ if (!isOpenInternal())
+ return false;
+
+ SqlQueryPtr results = exec("ROLLBACK;", Flag::NO_LOCK);
+ if (results->isError())
+ {
+ qCritical() << "Error while rolling back a transaction: " << results->getErrorCode() << results->getErrorText();
+ return false;
+ }
+
+ return true;
+}
+
QHash<QString, QVariant> AbstractDb::getAggregateContext(void* memPtr)
{
if (!memPtr)
@@ -792,55 +838,31 @@ quint32 AbstractDb::generateAsyncId()
return asyncId++;
}
-bool AbstractDb::begin()
+bool AbstractDb::begin(bool noLock)
{
- QWriteLocker locker(&dbOperLock);
-
- if (!isOpenInternal())
- return false;
-
- SqlQueryPtr results = exec("BEGIN;", Flag::NO_LOCK);
- if (results->isError())
- {
- qCritical() << "Error while starting a transaction: " << results->getErrorCode() << results->getErrorText();
- return false;
- }
+ if (noLock)
+ return beginNoLock();
- return true;
+ QWriteLocker locker(&dbOperLock);
+ return beginNoLock();
}
-bool AbstractDb::commit()
+bool AbstractDb::commit(bool noLock)
{
- QWriteLocker locker(&dbOperLock);
-
- if (!isOpenInternal())
- return false;
-
- SqlQueryPtr results = exec("COMMIT;", Flag::NO_LOCK);
- if (results->isError())
- {
- qCritical() << "Error while committing a transaction: " << results->getErrorCode() << results->getErrorText();
- return false;
- }
+ if (noLock)
+ return commitNoLock();
- return true;
+ QWriteLocker locker(&dbOperLock);
+ return commitNoLock();
}
-bool AbstractDb::rollback()
+bool AbstractDb::rollback(bool noLock)
{
- QWriteLocker locker(&dbOperLock);
-
- if (!isOpenInternal())
- return false;
-
- SqlQueryPtr results = exec("ROLLBACK;", Flag::NO_LOCK);
- if (results->isError())
- {
- qCritical() << "Error while rolling back a transaction: " << results->getErrorCode() << results->getErrorText();
- return false;
- }
+ if (noLock)
+ return rollbackNoLock();
- return true;
+ QWriteLocker locker(&dbOperLock);
+ return rollbackNoLock();
}
void AbstractDb::interrupt()
@@ -915,7 +937,15 @@ void AbstractDb::registerFunction(const AbstractDb::RegisteredFunction& function
void AbstractDb::flushWal()
{
- if (!flushWalInternal())
+ if (flushWalInternal())
+ {
+ if (exec("PRAGMA journal_mode")->getSingleCell().toString() == "wal")
+ {
+ exec("PRAGMA journal_mode = delete;", Flag::ZERO_TIMEOUT);
+ exec("PRAGMA journal_mode = wal;", Flag::ZERO_TIMEOUT);
+ }
+ }
+ else
notifyWarn(tr("Failed to make full WAL checkpoint on database '%1'. Error returned from SQLite engine: %2").arg(name, getErrorTextInternal()));
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.h b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.h
index 193f173..0b69916 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb.h
@@ -64,9 +64,9 @@ class API_EXPORT AbstractDb : public Db
quint32 asyncExec(const QString& query, const QList<QVariant>& args, Flags flags = Flag::NONE);
quint32 asyncExec(const QString& query, const QHash<QString, QVariant>& args, Flags flags = Flag::NONE);
quint32 asyncExec(const QString& query, Flags flags = Flag::NONE);
- bool begin();
- bool commit();
- bool rollback();
+ bool begin(bool noLock = false);
+ bool commit(bool noLock = false);
+ bool rollback(bool noLock = false);
void interrupt();
void asyncInterrupt();
bool isReadable();
@@ -209,6 +209,9 @@ class API_EXPORT AbstractDb : public Db
bool registerCollation(const QString& name);
bool deregisterCollation(const QString& name);
bool isCollationRegistered(const QString& name);
+ bool beginNoLock();
+ bool commitNoLock();
+ bool rollbackNoLock();
/**
* @brief Registers a collation sequence implementation in the database.
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb3.h b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb3.h
index f8812e9..d1831e2 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/abstractdb3.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/abstractdb3.h
@@ -65,6 +65,7 @@ class AbstractDb3 : public AbstractDb
bool registerAggregateFunction(const QString& name, int argCount, bool deterministic);
bool registerCollationInternal(const QString& name);
bool deregisterCollationInternal(const QString& name);
+ bool isTransactionActive() const;
private:
class Query : public SqlQuery
@@ -362,7 +363,7 @@ QList<AliasedColumn> AbstractDb3<T>::columnsForQuery(const QString& query)
return result;
}
- if (tail && !QString::fromUtf8(tail).trimmed().isEmpty())
+ if (tail && !QString::fromUtf8(tail).trimmed().isEmpty() && !removeComments(QString::fromUtf8(tail)).trimmed().isEmpty())
qWarning() << "Executed query left with tailing contents:" << tail << ", while finding columns for query:" << query;
@@ -556,6 +557,12 @@ bool AbstractDb3<T>::registerCollationInternal(const QString& name)
if (!dbHandle)
return false;
+ CollationManager::CollationPtr collation = COLLATIONS->getCollation(name);
+ if (collation == nullptr)
+ return false;
+ if (collation->type == CollationManager::CollationType::EXTENSION_BASED)
+ return !(exec(collation->code, Flag::NO_LOCK)->isError());
+
CollationUserData* userData = new CollationUserData;
userData->name = name;
@@ -875,6 +882,15 @@ void AbstractDb3<T>::registerDefaultCollationRequestHandler()
qWarning() << "Could not register default collation request handler. Unknown collations will cause errors.";
}
+template <class T>
+bool AbstractDb3<T>::isTransactionActive() const
+{
+ if (!dbHandle)
+ return false;
+
+ return !T::get_autocommit(dbHandle);
+}
+
//------------------------------------------------------------------------------------
// Results
//------------------------------------------------------------------------------------
@@ -940,7 +956,7 @@ int AbstractDb3<T>::Query::prepareStmt()
return res;
}
- if (tail && !QString::fromUtf8(tail).trimmed().isEmpty())
+ if (tail && !QString::fromUtf8(tail).trimmed().isEmpty() && !removeComments(QString::fromUtf8(tail)).trimmed().isEmpty())
qWarning() << "Executed query left with tailing contents:" << tail << ", while executing query:" << query;
return T::OK;
@@ -1189,14 +1205,14 @@ int AbstractDb3<T>::Query::fetchFirst()
for (int i = 0; i < colCount; i++)
colNames << QString::fromUtf8(T::column_name(stmt, i));
- int changesBefore = T::total_changes(db->dbHandle);
+ qint64 changesBefore = T::total_changes64(db->dbHandle);
rowAvailable = true;
int res = fetchNext();
affected = 0;
if (res == T::OK)
{
- affected = T::total_changes(db->dbHandle) - changesBefore;
+ affected = T::total_changes64(db->dbHandle) - changesBefore;
insertRowId["ROWID"] = T::last_insert_rowid(db->dbHandle);
}
@@ -1218,7 +1234,8 @@ int AbstractDb3<T>::Query::fetchNext()
rowAvailable = false;
int res;
int secondsSpent = 0;
- while ((res = T::step(stmt)) == T::BUSY && secondsSpent < db->getTimeout())
+ bool zeroTimeout = flags.testFlag(Db::Flag::ZERO_TIMEOUT);
+ while ((res = T::step(stmt)) == T::BUSY && !zeroTimeout && secondsSpent < db->getTimeout() && !T::is_interrupted(db->dbHandle))
{
QThread::sleep(1);
if (db->getTimeout() >= 0)
@@ -1233,6 +1250,9 @@ int AbstractDb3<T>::Query::fetchNext()
case T::DONE:
// Empty pointer as no more results are available.
break;
+ case T::INTERRUPT:
+ setError(res, QString::fromUtf8(T::errmsg(db->dbHandle)));
+ return T::INTERRUPT;
default:
setError(res, QString::fromUtf8(T::errmsg(db->dbHandle)));
return T::ERROR;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/db.h b/SQLiteStudio3/coreSQLiteStudio/db/db.h
index 1331fff..f81d901 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/db.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/db.h
@@ -137,20 +137,22 @@ class API_EXPORT Db : public QObject, public Interruptable
*/
enum class Flag
{
- NONE = 0x0, /**< No flags. This is default. */
- PRELOAD = 0x1, /**< Preloads all execution results into the results object. Useful for asynchronous execution. */
- NO_LOCK = 0x2, /**<
- * Prevents SQLiteStudio from setting the lock for execution on this base (not the SQLite lock,
- * just a Db internal lock for multi-threading access to the Db::exec()). This should be used
- * only in justified circumstances. That is when the Db call has to be done from within the part
- * of code, where the lock on Db was already set. Never (!) use this to ommit lock from different
- * threads. Justified situation is when you implement Db::initialDbSetup() in the derived class,
- * or when you implement SqlFunctionPlugin. Don't use it for the usual cases.
- */
- SKIP_DROP_DETECTION = 0x4, /**< Query execution will not notify about any detected objects dropped by the query.
- * Benefit is that it speeds up execution. */
- SKIP_PARAM_COUNTING = 0x8, /**< During execution with arguments as list the number of bind parameters will not be verified.
- * This speeds up execution at cost of possible error if bind params in query don't match number of args. */
+ NONE = 0x00, /**< No flags. This is default. */
+ PRELOAD = 0x01, /**< Preloads all execution results into the results object. Useful for asynchronous execution. */
+ NO_LOCK = 0x02, /**<
+ * Prevents SQLiteStudio from setting the lock for execution on this base (not the SQLite lock,
+ * just a Db internal lock for multi-threading access to the Db::exec()). This should be used
+ * only in justified circumstances. That is when the Db call has to be done from within the part
+ * of code, where the lock on Db was already set. Never (!) use this to ommit lock from different
+ * threads. Justified situation is when you implement Db::initialDbSetup() in the derived class,
+ * or when you implement SqlFunctionPlugin. Don't use it for the usual cases.
+ */
+ SKIP_DROP_DETECTION = 0x04, /**< Query execution will not notify about any detected objects dropped by the query.
+ * Benefit is that it speeds up execution. */
+ SKIP_PARAM_COUNTING = 0x08, /**< During execution with arguments as list the number of bind parameters will not be verified.
+ * This speeds up execution at cost of possible error if bind params in query don't match number of args. */
+ ZERO_TIMEOUT = 0x10, /**< By default, if database returns SQLITE_BUSY, the app will wait up until configured timeout and fail then.
+ * With this flag, there will be no waiting for this particular execution, but it will fail fast. */
};
Q_DECLARE_FLAGS(Flags, Flag)
@@ -453,19 +455,19 @@ class API_EXPORT Db : public QObject, public Interruptable
*
* This method uses basic "BEGIN" statement to begin transaction, therefore recurrent transactions are not supported.
*/
- virtual bool begin() = 0;
+ virtual bool begin(bool noLock = false) = 0;
/**
* @brief Commits SQL transaction.
* @return true on success, or false otherwise.
*/
- virtual bool commit() = 0;
+ virtual bool commit(bool noLock = false) = 0;
/**
* @brief Rolls back the transaction.
* @return true on success, or false otherwise (i.e. there was no transaction open, there was a connection problem, etc).
*/
- virtual bool rollback() = 0;
+ virtual bool rollback(bool noLock = false) = 0;
/**
* @brief Interrupts current execution asynchronously.
@@ -725,6 +727,12 @@ class API_EXPORT Db : public QObject, public Interruptable
*/
virtual Db* clone() const = 0;
+ /**
+ * @brief Checkes if there is an ongoing transaction at the moment.
+ * @return true if there is an active transaction at the moment, or false otherwise.
+ */
+ virtual bool isTransactionActive() const = 0;
+
signals:
/**
* @brief Emitted when the connection to the database was established.
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.cpp b/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.cpp
index 76ddd20..296b7d1 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.cpp
@@ -15,6 +15,21 @@ bool DbSqlite3::complete(const QString& sql)
return Sqlite3::complete(sql.toUtf8().constData());
}
+bool DbSqlite3::isDbFile(const QString &path)
+{
+ QFile file(path);
+ if (!file.open(QIODevice::ReadOnly)) {
+ return false;
+ }
+
+ QByteArray data = file.read(16);
+ file.close();
+ if (data.size() < 16)
+ return false;
+
+ return data == QByteArrayLiteral("SQLite format 3\000");
+}
+
Db* DbSqlite3::clone() const
{
return new DbSqlite3(name, path, connOptions);
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.h b/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.h
index 54a4230..90e3245 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/dbsqlite3.h
@@ -29,6 +29,7 @@ class API_EXPORT DbSqlite3 : public AbstractDb3<Sqlite3>
DbSqlite3(const QString& name, const QString& path);
static bool complete(const QString& sql);
+ static bool isDbFile(const QString& path);
Db* clone() const;
QString getTypeClassName() const;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.cpp b/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.cpp
index e001017..541a03e 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.cpp
@@ -164,18 +164,21 @@ SqlQueryPtr InvalidDb::prepare(const QString& query)
return SqlQueryPtr();
}
-bool InvalidDb::begin()
+bool InvalidDb::begin(bool noLock)
{
+ UNUSED(noLock);
return false;
}
-bool InvalidDb::commit()
+bool InvalidDb::commit(bool noLock)
{
+ UNUSED(noLock);
return false;
}
-bool InvalidDb::rollback()
+bool InvalidDb::rollback(bool noLock)
{
+ UNUSED(noLock);
return false;
}
@@ -351,6 +354,11 @@ Db* InvalidDb::clone() const
return new InvalidDb(name, path, connOptions);
}
+bool InvalidDb::isTransactionActive() const
+{
+ return false;
+}
+
void InvalidDb::interrupt()
{
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.h b/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.h
index 2505079..edb2e06 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/invaliddb.h
@@ -33,9 +33,9 @@ class API_EXPORT InvalidDb : public Db
quint32 asyncExec(const QString& query, const QHash<QString, QVariant>& args, Flags flags);
quint32 asyncExec(const QString& query, Flags flags);
SqlQueryPtr prepare(const QString& query);
- bool begin();
- bool commit();
- bool rollback();
+ bool begin(bool noLock = false);
+ bool commit(bool noLock = false);
+ bool rollback(bool noLock = false);
void asyncInterrupt();
bool isReadable();
bool isWritable();
@@ -63,6 +63,7 @@ class API_EXPORT InvalidDb : public Db
bool loadExtension(const QString& filePath, const QString& initFunc);
bool isComplete(const QString& sql) const;
Db* clone() const;
+ bool isTransactionActive() const;
public slots:
bool open();
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.cpp
index 022bf47..dff770b 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.cpp
@@ -3,6 +3,7 @@
#include "sqlerrorcodes.h"
#include "services/dbmanager.h"
#include "db/sqlerrorcodes.h"
+#include "db/dbsqlite3.h"
#include "services/notifymanager.h"
#include "queryexecutorsteps/queryexecutoraddrowids.h"
#include "queryexecutorsteps/queryexecutorcolumns.h"
@@ -19,6 +20,7 @@
#include "queryexecutorsteps/queryexecutordetectschemaalter.h"
#include "queryexecutorsteps/queryexecutorvaluesmode.h"
#include "queryexecutorsteps/queryexecutorcolumntype.h"
+#include "db/queryexecutorsteps/queryexecutorsmarthints.h"
#include "common/unused.h"
#include "chainexecutor.h"
#include "log.h"
@@ -30,6 +32,7 @@
#include <QThreadPool>
#include <QDebug>
#include <QtMath>
+#include <dbattacher.h>
// TODO modify all executor steps to use rebuildTokensFromContents() method, instead of replacing tokens manually.
@@ -55,8 +58,14 @@ QueryExecutor::QueryExecutor(Db* db, const QString& query, QObject *parent) :
QueryExecutor::~QueryExecutor()
{
- delete context;
- context = nullptr;
+ safe_delete(context);
+ if (countingDb)
+ {
+ if (countingDb->isOpen())
+ countingDb->closeQuiet();
+
+ delete countingDb;
+ }
}
void QueryExecutor::setupExecutionChain()
@@ -128,6 +137,7 @@ void QueryExecutor::setupExecutionChain()
executionChain.append(createSteps(LAST));
executionChain << new QueryExecutorExecute();
+ executionChain << new QueryExecutorSmartHints(); // must be last, as it queries schema and execution might modify schema
for (QueryExecutorStep*& step : executionChain)
step->init(this, context);
@@ -247,6 +257,9 @@ void QueryExecutor::exec(Db::QueryResultsHandler resultsHandler)
executionInProgress = true;
executionMutex.unlock();
+ if (countingDb && countingDb->isOpen())
+ countingDb->interrupt();
+
this->resultsHandler = resultsHandler;
if (asyncMode)
@@ -271,7 +284,7 @@ void QueryExecutor::execInternal()
if (queryCountLimitForSmartMode > -1)
{
- queriesForSimpleExecution = quickSplitQueries(originalQuery, false, true);
+ queriesForSimpleExecution = splitQueries(originalQuery, false, true);
int queryCount = queriesForSimpleExecution.size();
if (queryCount > queryCountLimitForSmartMode)
{
@@ -285,13 +298,6 @@ void QueryExecutor::execInternal()
simpleExecution = false;
interrupted = false;
- if (resultsCountingAsyncId != 0)
- {
- resultsCountingAsyncId = 0;
- db->interrupt();
- releaseResultsAndCleanup();
- }
-
// Reset context
delete context;
context = new Context();
@@ -329,35 +335,48 @@ bool QueryExecutor::countResults()
if (context->countingQuery.isEmpty()) // simple method doesn't provide that
return false;
- if (asyncMode)
+ if (!countingDb)
+ return false; // no db defined, so no countingDb defined
+
+ if (!countingDb->isOpen() && !countingDb->openQuiet())
{
- // Start asynchronous results counting query
- resultsCountingAsyncId = db->asyncExec(context->countingQuery, context->queryParameters, Db::Flag::NO_LOCK);
+ notifyError(tr("An error occured while executing the count(*) query, thus data paging will be disabled. Error details from the database: %1")
+ .arg("Failed to establish dedicated connection for results counting."));
+ return false;
}
- else
- {
- SqlQueryPtr results = db->exec(context->countingQuery, context->queryParameters, Db::Flag::NO_LOCK);
- context->totalRowsReturned = results->getSingleCell().toLongLong();
- context->totalPages = (int)qCeil(((double)(context->totalRowsReturned)) / ((double)getResultsPerPage()));
-
- emit resultsCountingFinished(context->rowsAffected, context->totalRowsReturned, context->totalPages);
- if (results->isError())
+ // Apply all transparent attaches to the counting DB
+ auto it = context->dbNameToAttach.iterator();
+ while (it.hasNext())
+ {
+ auto entry = it.next();
+ Db* dbToAttach = DBLIST->getByName(entry.key());
+ SqlQueryPtr attachRes = countingDb->exec(QString("ATTACH '%1' AS %2").arg(dbToAttach->getPath(), entry.value()));
+ if (attachRes->isError())
{
notifyError(tr("An error occured while executing the count(*) query, thus data paging will be disabled. Error details from the database: %1")
- .arg(results->getErrorText()));
+ .arg("Failed to attach necessary databases for counting."));
+
+ qDebug() << "Error while attaching db for counting:" << attachRes->getErrorText();
+ countingDb->detachAll();
return false;
}
}
- return true;
-}
-void QueryExecutor::dbAsyncExecFinished(quint32 asyncId, SqlQueryPtr results)
-{
- if (handleRowCountingResults(asyncId, results))
- return;
-
- // If this was raised by any other asyncExec, handle it here.
+ if (asyncMode)
+ {
+ // Start asynchronous results counting query
+ countingDb->asyncExec(context->countingQuery, context->queryParameters, [=](SqlQueryPtr results)
+ {
+ handleRowCountingResults(results);
+ }, Db::Flag::PRELOAD);
+ }
+ else
+ {
+ SqlQueryPtr results = countingDb->exec(context->countingQuery, context->queryParameters, Db::Flag::PRELOAD);
+ handleRowCountingResults(results);
+ }
+ return true;
}
qint64 QueryExecutor::getLastExecutionTime() const
@@ -449,7 +468,7 @@ void QueryExecutor::executeSimpleMethod()
simpleExecution = true;
context->editionForbiddenReasons << EditionForbiddenReason::SMART_EXECUTION_FAILED;
if (queriesForSimpleExecution.isEmpty())
- queriesForSimpleExecution = quickSplitQueries(originalQuery, false, true);
+ queriesForSimpleExecution = splitQueries(originalQuery, false, true);
QStringList queriesWithPagination = applyFiltersAndLimitAndOrderForSimpleMethod(queriesForSimpleExecution);
if (isExecutorLoggingEnabled())
@@ -573,30 +592,23 @@ void QueryExecutor::cleanup()
}
}
-bool QueryExecutor::handleRowCountingResults(quint32 asyncId, SqlQueryPtr results)
+bool QueryExecutor::handleRowCountingResults(SqlQueryPtr results)
{
- if (resultsCountingAsyncId == 0)
- return false;
-
- if (resultsCountingAsyncId != asyncId)
- return false;
-
if (isExecutionInProgress()) // shouldn't be true, but just in case
return false;
- resultsCountingAsyncId = 0;
-
context->totalRowsReturned = results->getSingleCell().toLongLong();
context->totalPages = (int)qCeil(((double)(context->totalRowsReturned)) / ((double)getResultsPerPage()));
emit resultsCountingFinished(context->rowsAffected, context->totalRowsReturned, context->totalPages);
- if (results->isError())
+ if (results->isError() && results->getErrorCode() != Sqlite3::INTERRUPT)
{
notifyError(tr("An error occured while executing the count(*) query, thus data paging will be disabled. Error details from the database: %1")
.arg(results->getErrorText()));
}
+ countingDb->detachAll();
return true;
}
@@ -872,13 +884,15 @@ Db* QueryExecutor::getDb() const
void QueryExecutor::setDb(Db* value)
{
- if (db)
- disconnect(db, SIGNAL(asyncExecFinished(quint32,SqlQueryPtr)), this, SLOT(dbAsyncExecFinished(quint32,SqlQueryPtr)));
-
db = value;
+ if (countingDb)
+ {
+ countingDb->closeQuiet();
+ safe_delete(countingDb);
+ }
if (db)
- connect(db, SIGNAL(asyncExecFinished(quint32,SqlQueryPtr)), this, SLOT(dbAsyncExecFinished(quint32,SqlQueryPtr)));
+ countingDb = db->clone();
}
bool QueryExecutor::getSkipRowCounting() const
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.h b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.h
index c8d0b00..5c710a4 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutor.h
@@ -177,6 +177,10 @@ class API_EXPORT QueryExecutor : public QObject, public QRunnable
* The data cell comes from a VIEW that was not expanded (because there were
* multi-level views), therefore it was impossible to get ROWID for the cell.
*/
+ RES_INLINE_SUBSEL,/**<
+ * The data cell comes from an subselect used as inline expression of result column.
+ * Getting ROWID of such cell is not possible.
+ */
};
/**
@@ -1224,17 +1228,14 @@ class API_EXPORT QueryExecutor : public QObject, public QRunnable
/**
* @brief Extracts counting query results.
- * @param asyncId Asynchronous ID of the counting query execution.
* @param results Results from the counting query execution.
- * @return true if passed asyncId is the one for currently running counting query, or false otherwise.
- *
- * It's called from database asynchronous execution thread. The database might have executed
- * some other acynchronous queries too, so this method checks if the asyncId is the expected one.
+ * @return true if counting was successful, i.e. there is no ongoing query execution, or false otherwise.
*
+ * It may be called from database asynchronous execution thread.
* Basicly this method is called a result of countResults() call. Extracts counted number of rows
* and stores it in query executor's context.
*/
- bool handleRowCountingResults(quint32 asyncId, SqlQueryPtr results);
+ bool handleRowCountingResults(SqlQueryPtr results);
QStringList applyFiltersAndLimitAndOrderForSimpleMethod(const QStringList &queries);
@@ -1385,14 +1386,6 @@ class API_EXPORT QueryExecutor : public QObject, public QRunnable
qint64 simpleExecutionStartTime;
/**
- * @brief Asynchronous ID of counting query execution.
- *
- * Asynchronous ID returned from Db::asyncExec() for the counting query execution.
- * See countResults() for details on counting query.
- */
- quint32 resultsCountingAsyncId = 0;
-
- /**
* @brief Flag indicating results preloading.
*
* See Context::preloadResults.
@@ -1494,6 +1487,8 @@ class API_EXPORT QueryExecutor : public QObject, public QRunnable
bool forceSimpleMode = false;
ChainExecutor* simpleExecutor = nullptr;
+ Db* countingDb = nullptr;
+ QStringList countingAttaches;
signals:
/**
@@ -1581,17 +1576,6 @@ class API_EXPORT QueryExecutor : public QObject, public QRunnable
* In case of success emits executionFinished(), in case of error emits executionFailed().
*/
void simpleExecutionFinished(SqlQueryPtr results);
-
- /**
- * @brief Handles asynchronous database execution results.
- * @param asyncId Asynchronous ID of the execution.
- * @param results Results from the execution.
- *
- * QueryExecutor checks whether the \p asyncId belongs to the counting query execution,
- * or the simple execution.
- * Dispatches query results to a proper handler method.
- */
- void dbAsyncExecFinished(quint32 asyncId, SqlQueryPtr results);
};
int qHash(QueryExecutor::EditionForbiddenReason reason);
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutoraddrowids.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutoraddrowids.cpp
index d294b2c..5347169 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutoraddrowids.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutoraddrowids.cpp
@@ -61,7 +61,7 @@ QHash<SelectResolver::Table,QHash<QString,QString>> QueryExecutorAddRowIds::addR
return rowIdColsMap;
}
- core->rebuildTokens();
+ select->rebuildTokens();
// Getting all tables we need to get ROWID for
SelectResolver resolver(db, select->tokens.detokenize(), context->dbNameToAttach);
@@ -71,7 +71,7 @@ QHash<SelectResolver::Table,QHash<QString,QString>> QueryExecutorAddRowIds::addR
for (const SelectResolver::Table& table : tables)
{
if (table.flags & (SelectResolver::FROM_COMPOUND_SELECT | SelectResolver::FROM_DISTINCT_SELECT | SelectResolver::FROM_GROUPED_SELECT |
- SelectResolver::FROM_CTE_SELECT))
+ SelectResolver::FROM_CTE_SELECT | SelectResolver::FROM_TABLE_VALUED_FN | SelectResolver::FROM_RES_COL_SUBSELECT))
continue; // we don't get ROWID from compound, distinct or aggregated subselects.
// Tables from inside of view don't provide ROWID, if views were not expanded.
@@ -161,8 +161,11 @@ bool QueryExecutorAddRowIds::addResultColumns(SqliteSelect::Core* core, const Se
QHash<SelectResolver::Table,QHash<QString,QString>>& rowIdColsMap, bool isTopSelect)
{
SelectResolver::Table destilledTable = table;
- if (destilledTable.database == "main" && destilledTable.originalDatabase.isNull())
+ if (destilledTable.database.toLower() == "main" && (destilledTable.originalDatabase.isNull() || destilledTable.originalDatabase.toLower() == "main"))
+ {
destilledTable.database = QString();
+ destilledTable.originalDatabase = QString();
+ }
SelectResolver::Table keyTable = destilledTable;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.cpp
index d3f2eea..b447f84 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.cpp
@@ -69,13 +69,15 @@ bool QueryExecutorColumns::exec()
context->resultColumns << resultColumn; // store it in context for later usage by any step
}
-// qDebug() << "before: " << context->processedQuery;
+ //qDebug() << "before: " << context->processedQuery;
// Update query
select->rebuildTokens();
- wrapWithAliasedColumns(select.data());
+ // #5179 does not seem to be needed anymore, because query executor alias is applied always in the main column loop above.
+ // Keeping the commented reference here for a while, but to be removed in future (due to end of 2025).
+ //wrapWithAliasedColumns(select.data());
updateQueries();
-// qDebug() << "after: " << context->processedQuery;
+ //qDebug() << "after: " << context->processedQuery;
return true;
}
@@ -111,6 +113,9 @@ QueryExecutor::ResultColumnPtr QueryExecutorColumns::getResultColumn(const Selec
if (resolvedColumn.flags & SelectResolver::FROM_VIEW)
resultColumn->editionForbiddenReasons << QueryExecutor::ColumnEditionForbiddenReason::VIEW_NOT_EXPANDED;
+ if (resolvedColumn.flags & SelectResolver::FROM_RES_COL_SUBSELECT)
+ resultColumn->editionForbiddenReasons << QueryExecutor::ColumnEditionForbiddenReason::RES_INLINE_SUBSEL;
+
resultColumn->database = resolvedColumn.originalDatabase;
resultColumn->table = resolvedColumn.table;
resultColumn->column = resolvedColumn.column;
@@ -173,11 +178,13 @@ SqliteSelect::Core::ResultColumn* QueryExecutorColumns::getResultColumnForSelect
}
}
- selectResultColumn->asKw = true;
if (!col.alias.isNull())
- selectResultColumn->alias = col.alias;
- else
- selectResultColumn->alias = resultColumn->queryExecutorAlias;
+ selectResultColumn->expr->column = col.alias;
+
+ // #5179 duplicate of the same source table columns (but with different table alias) requires executor alias to be applied
+ // always and immediately here to get proper results.
+ selectResultColumn->asKw = true;
+ selectResultColumn->alias = resultColumn->queryExecutorAlias;
// If this alias was already used we need to use sequential alias
static_qstring(aliasTpl, "%1:%2");
@@ -209,63 +216,6 @@ bool QueryExecutorColumns::isRowIdColumnAlias(const QString& alias)
return false;
}
-void QueryExecutorColumns::wrapWithAliasedColumns(SqliteSelect* select)
-{
- // Wrap everything in a surrounding SELECT and given query executor alias to all columns this time
- TokenList sepTokens;
- sepTokens << TokenPtr::create(Token::OPERATOR, ",") << TokenPtr::create(Token::SPACE, " ");
-
- bool first = true;
- TokenList outerColumns;
- QStringList columnNamesUsed;
- QString baseColName;
- QString colName;
- static_qstring(colNameTpl, "%1:%2");
- for (QueryExecutor::ResultColumnPtr& resCol : context->resultColumns)
- {
- if (!first)
- outerColumns += sepTokens;
-
- // If alias was given, we use it. If it was anything but expression, we also use its display name,
- // because it's explicit column (no matter if from table, or table alias).
- baseColName = QString();
- if (!resCol->queryExecutorAlias.isNull())
- baseColName = resCol->alias;
- else if (!resCol->expression)
- baseColName = resCol->column;
-
- if (!baseColName.isNull())
- {
- colName = baseColName;
- for (int i = 1; columnNamesUsed.contains(colName, Qt::CaseInsensitive); i++)
- colName = colNameTpl.arg(resCol->column, QString::number(i));
-
- columnNamesUsed << colName;
- outerColumns << TokenPtr::create(Token::OTHER, wrapObjIfNeeded(colName));
- outerColumns << TokenPtr::create(Token::SPACE, " ");
- outerColumns << TokenPtr::create(Token::KEYWORD, "AS");
- outerColumns << TokenPtr::create(Token::SPACE, " ");
- }
- outerColumns << TokenPtr::create(Token::OTHER, resCol->queryExecutorAlias);
- first = false;
- }
-
- for (QueryExecutor::ResultRowIdColumnPtr& rowIdColumn : context->rowIdColumns)
- {
- for (QString& alias : rowIdColumn->queryExecutorAliasToColumn.keys())
- {
- if (!first)
- outerColumns += sepTokens;
-
- outerColumns << TokenPtr::create(Token::OTHER, alias);
- first = false;
- }
- }
-
- //QString t = outerColumns.detokenize(); // keeping it for debug purposes
- select->tokens = wrapSelect(select->tokens, outerColumns);
-}
-
bool QueryExecutorColumns::isRowIdColumn(const QString& columnAlias)
{
// In case of "SELECT * FROM (SELECT * FROM test);" the SelectResolver will return ROWID columns twice for each table listed,
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.h b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.h
index 8e1ebd2..e5650cb 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorcolumns.h
@@ -66,7 +66,6 @@ class QueryExecutorColumns : public QueryExecutorStep
*/
bool isRowIdColumnAlias(const QString& alias);
- void wrapWithAliasedColumns(SqliteSelect* select);
bool isRowIdColumn(const QString& columnAlias);
QStringList rowIdColNames;
};
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorexecute.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorexecute.cpp
index 1ffc1bf..cbb385c 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorexecute.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorexecute.cpp
@@ -14,7 +14,7 @@
bool QueryExecutorExecute::exec()
{
-// qDebug() << "q:" << context->processedQuery;
+ //qDebug() << "q:" << context->processedQuery;
startTime = QDateTime::currentMSecsSinceEpoch();
return executeQueries();
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorfilter.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorfilter.cpp
index bcc9ce4..af3ec9b 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorfilter.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorfilter.cpp
@@ -5,9 +5,6 @@ bool QueryExecutorFilter::exec()
{
// qDebug() << "filters:" << queryExecutor->getFilters();
// qDebug() << "q1:" << context->processedQuery;
- if (queryExecutor->getFilters().trimmed().isEmpty())
- return true;
-
SqliteSelectPtr select = getSelect();
if (!select || select->explain)
return true;
@@ -15,8 +12,20 @@ bool QueryExecutorFilter::exec()
if (select->tokens.size() < 1)
return true; // shouldn't happen, but if happens, quit gracefully
+ static_qstring(selectNoFiltersTpl, "SELECT * FROM (%1)");
static_qstring(selectTpl, "SELECT * FROM (%1) WHERE %2");
- QString newSelect = selectTpl.arg(select->detokenize(), queryExecutor->getFilters());
+
+ // Even without filters defined, the subselect is needed, because as it turns out (#5065)
+ // certain column names are implicitly aliased when occur in subselects.
+ // For example column "true" will be renamed to "columnN" if selected in subselect,
+ // but will not be aliased if it's selected in 1-level select.
+ // Because of that query executor provided inconsistent column aliases depending
+ // on whether the filter was defined or not.
+ QString newSelect = queryExecutor->getFilters().trimmed().isEmpty() ?
+ selectNoFiltersTpl.arg(select->detokenize()) :
+ selectTpl.arg(select->detokenize(), queryExecutor->getFilters());
+
+ //qDebug() << "filter:" << queryExecutor->getFilters();
int begin = select->tokens.first()->start;
int length = select->tokens.last()->end - select->tokens.first()->start + 1;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorlimit.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorlimit.cpp
index afa1297..95d48c8 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorlimit.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorlimit.cpp
@@ -1,3 +1,4 @@
+
#include "queryexecutorlimit.h"
#include <QDebug>
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutororder.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutororder.cpp
index 65bb0f6..753adf4 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutororder.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutororder.cpp
@@ -18,7 +18,11 @@ bool QueryExecutorOrder::exec()
TokenList tokens = getOrderTokens(sortOrder);
if (tokens.size() == 0)
- return false;
+ {
+ // happens in cases like #4819
+ queryExecutor->setSortOrder(QueryExecutor::SortList());
+ return true;
+ }
static_qstring(selectTpl, "SELECT * FROM (%1) ORDER BY %2");
QString newSelect = selectTpl.arg(select->detokenize(), tokens.detokenize());
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorreplaceviews.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorreplaceviews.cpp
index b6db4b2..4bd6739 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorreplaceviews.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorreplaceviews.cpp
@@ -109,12 +109,19 @@ void QueryExecutorReplaceViews::replaceViews(SqliteSelect* select)
QString alias = pair.first->alias.isNull() ? view->view : pair.first->alias;
- pair.first->select = view->select;
- pair.first->alias = alias;
- pair.first->database = QString();
- pair.first->table = QString();
+ QString sql = view->equivalentSelectTokens().detokenize();
+ Parser parser;
+ if (!parser.parse(sql) || parser.getQueries().size() == 0)
+ qWarning() << "Couldn't replace view " << view->view << " by equivalent select " << sql;
+ else
+ {
+ pair.first->select = new SqliteSelect(*dynamic_cast<SqliteSelect *>(parser.getQueries().first().get()));
+ pair.first->alias = alias;
+ pair.first->database = QString();
+ pair.first->table = QString();
- // replaceViews(pair.first->select); // No recursion, as we avoid multi-level expanding.
+ // replaceViews(pair.first->select); // No recursion, as we avoid multi-level expanding.
+ }
}
context->viewsExpanded = true;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.cpp b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.cpp
new file mode 100644
index 0000000..bf5b18e
--- /dev/null
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.cpp
@@ -0,0 +1,80 @@
+#include "queryexecutorsmarthints.h"
+#include "parser/ast/sqlitecreatetable.h"
+#include "schemaresolver.h"
+#include "services/notifymanager.h"
+
+bool QueryExecutorSmartHints::exec()
+{
+ for (SqliteQueryPtr& query : context->parsedQueries)
+ {
+ checkForFkDataTypeMismatch(query);
+ }
+ return true;
+}
+
+void QueryExecutorSmartHints::checkForFkDataTypeMismatch(const SqliteQueryPtr& query) {
+ if (query->queryType != SqliteQueryType::CreateTable)
+ return;
+
+ SchemaResolver resolver(db);
+
+ SqliteCreateTablePtr createTable = query.dynamicCast<SqliteCreateTable>();
+ StrHash<StrHash<DataType>> fkTableColumnTypes;
+ StrHash<DataType> localColumnTypes;
+ for (SqliteCreateTable::Column*& col : createTable->columns)
+ {
+ DataType localColumnType = col->type ? col->type->toDataType() : DataType();
+ localColumnTypes[col->name] = localColumnType;
+
+ for (SqliteCreateTable::Column::Constraint*& constr : col->getConstraints(SqliteCreateTable::Column::Constraint::FOREIGN_KEY))
+ {
+ if (constr->foreignKey->indexedColumns.isEmpty())
+ continue;
+
+ QString fkTable = constr->foreignKey->foreignTable;
+ QString fkColumn = constr->foreignKey->indexedColumns.first()->name;
+
+ if (!fkTableColumnTypes.contains(fkTable, Qt::CaseInsensitive))
+ fkTableColumnTypes[fkTable] = resolver.getTableColumnDataTypesByName(fkTable);
+
+ StrHash<DataType> fkTypes = fkTableColumnTypes.value(fkTable, Qt::CaseInsensitive);
+ DataType fkType = fkTypes.value(fkColumn, Qt::CaseInsensitive);
+
+ checkForFkDataTypeMismatch(createTable->table, col->name, localColumnType, fkTable, fkColumn, fkType);
+ }
+ }
+
+ for (SqliteCreateTable::Constraint*& constr : createTable->getConstraints(SqliteCreateTable::Constraint::FOREIGN_KEY))
+ {
+ QList<SqliteIndexedColumn*> localColumns = constr->indexedColumns;
+ QList<SqliteIndexedColumn*> fkColumns = constr->foreignKey->indexedColumns;
+ QListIterator<SqliteIndexedColumn*> localColumnsIt(localColumns);
+ QListIterator<SqliteIndexedColumn*> fkColumnsIt(fkColumns);
+
+ QString fkTable = constr->foreignKey->foreignTable;
+ if (!fkTableColumnTypes.contains(fkTable, Qt::CaseInsensitive))
+ fkTableColumnTypes[fkTable] = resolver.getTableColumnDataTypesByName(fkTable);
+
+ StrHash<DataType> fkTypes = fkTableColumnTypes.value(fkTable, Qt::CaseInsensitive);
+
+ while (localColumnsIt.hasNext() && fkColumnsIt.hasNext())
+ {
+ QString localColumn = localColumnsIt.next()->name;
+ QString fkColumn = fkColumnsIt.next()->name;
+
+ DataType localType = localColumnTypes.value(localColumn, Qt::CaseInsensitive);
+ DataType fkType = fkTypes.value(fkColumn, Qt::CaseInsensitive);
+
+ checkForFkDataTypeMismatch(createTable->table, localColumn, localType, fkTable, fkColumn, fkType);
+ }
+ }
+}
+
+void QueryExecutorSmartHints::checkForFkDataTypeMismatch(const QString &localTable, const QString &localColumn, const DataType &localType, const QString &fkTable, const QString &fkColumn, const DataType &fkType)
+{
+ if (localType.toString().toLower().trimmed() != fkType.toString().toLower().trimmed())
+ {
+ notifyWarn(tr("Column %1 in table %2 is referencing column %3 in table %4, but these columns have different data types: %5 vs. %6. This may cause issues related to foreign key value matching.")
+ .arg(localColumn, localTable, fkColumn, fkTable, localType.toString(), fkType.toString()));
+ }
+}
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.h b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.h
new file mode 100644
index 0000000..91e96d6
--- /dev/null
+++ b/SQLiteStudio3/coreSQLiteStudio/db/queryexecutorsteps/queryexecutorsmarthints.h
@@ -0,0 +1,28 @@
+#ifndef QUERYEXECUTORSMARTHINTS_H
+#define QUERYEXECUTORSMARTHINTS_H
+
+#include "queryexecutorstep.h"
+
+class SqliteColumnType;
+
+/**
+ * @brief Analyzes executed query and gives useful hints to user.
+ *
+ * Originally this class was introduced to address the #4774 issue.
+ *
+ * Intention of this step is to find any useful hints that may be provided to user in the notification area.
+ */
+class QueryExecutorSmartHints : public QueryExecutorStep
+{
+ Q_OBJECT
+
+ public:
+ bool exec();
+
+ private:
+ void checkForFkDataTypeMismatch(const SqliteQueryPtr& query);
+ void checkForFkDataTypeMismatch(const QString& localTable, const QString& localColumn, const DataType& localType,
+ const QString& fkTable, const QString& fkColumn, const DataType& fkType);
+};
+
+#endif // QUERYEXECUTORSMARTHINTS_H
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/sqlite3.h b/SQLiteStudio3/coreSQLiteStudio/db/sqlite3.h
index 44e53ef..dbecc3f 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/sqlite3.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/sqlite3.h
@@ -43,7 +43,30 @@ extern "C" {
/*
-** Provide the ability to override linkage features of the interface.
+** Facilitate override of interface linkage and calling conventions.
+** Be aware that these macros may not be used within this particular
+** translation of the amalgamation and its associated header file.
+**
+** The SQLITE_EXTERN and SQLITE_API macros are used to instruct the
+** compiler that the target identifier should have external linkage.
+**
+** The SQLITE_CDECL macro is used to set the calling convention for
+** public functions that accept a variable number of arguments.
+**
+** The SQLITE_APICALL macro is used to set the calling convention for
+** public functions that accept a fixed number of arguments.
+**
+** The SQLITE_STDCALL macro is no longer used and is now deprecated.
+**
+** The SQLITE_CALLBACK macro is used to set the calling convention for
+** function pointers.
+**
+** The SQLITE_SYSAPI macro is used to set the calling convention for
+** functions provided by the operating system.
+**
+** Currently, the SQLITE_CDECL, SQLITE_APICALL, SQLITE_CALLBACK, and
+** SQLITE_SYSAPI macros are used only when building for environments
+** that require non-default calling conventions.
*/
#ifndef SQLITE_EXTERN
# define SQLITE_EXTERN extern
@@ -123,9 +146,9 @@ extern "C" {
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
** [sqlite_version()] and [sqlite_source_id()].
*/
-#define SQLITE_VERSION "3.34.1"
-#define SQLITE_VERSION_NUMBER 3034001
-#define SQLITE_SOURCE_ID "2021-01-20 14:10:07 10e20c0b43500cfb9bbc0eaa061c57514f715d87238f4d835880cd846b9ebd1f"
+#define SQLITE_VERSION "3.47.1"
+#define SQLITE_VERSION_NUMBER 3047001
+#define SQLITE_SOURCE_ID "2024-11-25 12:07:48 b95d11e958643b969c47a8e5857f3793b9e69700b8f1469371386369a26e577e"
/*
** CAPI3REF: Run-Time Library Version Numbers
@@ -397,6 +420,8 @@ typedef int (*sqlite3_callback)(void*,int,char**, char**);
** the 1st parameter to sqlite3_exec() while sqlite3_exec() is running.
** <li> The application must not modify the SQL statement text passed into
** the 2nd parameter of sqlite3_exec() while sqlite3_exec() is running.
+** <li> The application must not dereference the arrays or string pointers
+** passed as the 3rd and 4th callback parameters after it returns.
** </ul>
*/
SQLITE_API int sqlite3_exec(
@@ -505,6 +530,7 @@ SQLITE_API int sqlite3_exec(
#define SQLITE_IOERR_ROLLBACK_ATOMIC (SQLITE_IOERR | (31<<8))
#define SQLITE_IOERR_DATA (SQLITE_IOERR | (32<<8))
#define SQLITE_IOERR_CORRUPTFS (SQLITE_IOERR | (33<<8))
+#define SQLITE_IOERR_IN_PAGE (SQLITE_IOERR | (34<<8))
#define SQLITE_LOCKED_SHAREDCACHE (SQLITE_LOCKED | (1<<8))
#define SQLITE_LOCKED_VTAB (SQLITE_LOCKED | (2<<8))
#define SQLITE_BUSY_RECOVERY (SQLITE_BUSY | (1<<8))
@@ -537,12 +563,14 @@ SQLITE_API int sqlite3_exec(
#define SQLITE_CONSTRAINT_VTAB (SQLITE_CONSTRAINT | (9<<8))
#define SQLITE_CONSTRAINT_ROWID (SQLITE_CONSTRAINT |(10<<8))
#define SQLITE_CONSTRAINT_PINNED (SQLITE_CONSTRAINT |(11<<8))
+#define SQLITE_CONSTRAINT_DATATYPE (SQLITE_CONSTRAINT |(12<<8))
#define SQLITE_NOTICE_RECOVER_WAL (SQLITE_NOTICE | (1<<8))
#define SQLITE_NOTICE_RECOVER_ROLLBACK (SQLITE_NOTICE | (2<<8))
+#define SQLITE_NOTICE_RBU (SQLITE_NOTICE | (3<<8))
#define SQLITE_WARNING_AUTOINDEX (SQLITE_WARNING | (1<<8))
#define SQLITE_AUTH_USER (SQLITE_AUTH | (1<<8))
#define SQLITE_OK_LOAD_PERMANENTLY (SQLITE_OK | (1<<8))
-#define SQLITE_OK_SYMLINK (SQLITE_OK | (2<<8))
+#define SQLITE_OK_SYMLINK (SQLITE_OK | (2<<8)) /* internal use only */
/*
** CAPI3REF: Flags For File Open Operations
@@ -550,6 +578,19 @@ SQLITE_API int sqlite3_exec(
** These bit values are intended for use in the
** 3rd parameter to the [sqlite3_open_v2()] interface and
** in the 4th parameter to the [sqlite3_vfs.xOpen] method.
+**
+** Only those flags marked as "Ok for sqlite3_open_v2()" may be
+** used as the third argument to the [sqlite3_open_v2()] interface.
+** The other flags have historically been ignored by sqlite3_open_v2(),
+** though future versions of SQLite might change so that an error is
+** raised if any of the disallowed bits are passed into sqlite3_open_v2().
+** Applications should not depend on the historical behavior.
+**
+** Note in particular that passing the SQLITE_OPEN_EXCLUSIVE flag into
+** [sqlite3_open_v2()] does *not* cause the underlying database file
+** to be opened using O_EXCL. Passing SQLITE_OPEN_EXCLUSIVE into
+** [sqlite3_open_v2()] has historically be a no-op and might become an
+** error in future versions of SQLite.
*/
#define SQLITE_OPEN_READONLY 0x00000001 /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_READWRITE 0x00000002 /* Ok for sqlite3_open_v2() */
@@ -572,6 +613,7 @@ SQLITE_API int sqlite3_exec(
#define SQLITE_OPEN_PRIVATECACHE 0x00040000 /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_WAL 0x00080000 /* VFS only */
#define SQLITE_OPEN_NOFOLLOW 0x01000000 /* Ok for sqlite3_open_v2() */
+#define SQLITE_OPEN_EXRESCODE 0x02000000 /* Extended result codes */
/* Reserved: 0x00F00000 */
/* Legacy compatibility: */
@@ -610,6 +652,13 @@ SQLITE_API int sqlite3_exec(
** filesystem supports doing multiple write operations atomically when those
** write operations are bracketed by [SQLITE_FCNTL_BEGIN_ATOMIC_WRITE] and
** [SQLITE_FCNTL_COMMIT_ATOMIC_WRITE].
+**
+** The SQLITE_IOCAP_SUBPAGE_READ property means that it is ok to read
+** from the database file in amounts that are not a multiple of the
+** page size and that do not begin at a page boundary. Without this
+** property, SQLite is careful to only do full-page reads and write
+** on aligned pages, with the one exception that it will do a sub-page
+** read of the first page to access the database header.
*/
#define SQLITE_IOCAP_ATOMIC 0x00000001
#define SQLITE_IOCAP_ATOMIC512 0x00000002
@@ -626,19 +675,24 @@ SQLITE_API int sqlite3_exec(
#define SQLITE_IOCAP_POWERSAFE_OVERWRITE 0x00001000
#define SQLITE_IOCAP_IMMUTABLE 0x00002000
#define SQLITE_IOCAP_BATCH_ATOMIC 0x00004000
+#define SQLITE_IOCAP_SUBPAGE_READ 0x00008000
/*
** CAPI3REF: File Locking Levels
**
** SQLite uses one of these integer values as the second
** argument to calls it makes to the xLock() and xUnlock() methods
-** of an [sqlite3_io_methods] object.
+** of an [sqlite3_io_methods] object. These values are ordered from
+** lest restrictive to most restrictive.
+**
+** The argument to xLock() is always SHARED or higher. The argument to
+** xUnlock is either SHARED or NONE.
*/
-#define SQLITE_LOCK_NONE 0
-#define SQLITE_LOCK_SHARED 1
-#define SQLITE_LOCK_RESERVED 2
-#define SQLITE_LOCK_PENDING 3
-#define SQLITE_LOCK_EXCLUSIVE 4
+#define SQLITE_LOCK_NONE 0 /* xUnlock() only */
+#define SQLITE_LOCK_SHARED 1 /* xLock() or xUnlock() */
+#define SQLITE_LOCK_RESERVED 2 /* xLock() only */
+#define SQLITE_LOCK_PENDING 3 /* xLock() only */
+#define SQLITE_LOCK_EXCLUSIVE 4 /* xLock() only */
/*
** CAPI3REF: Synchronization Type Flags
@@ -716,11 +770,18 @@ struct sqlite3_file {
** <li> [SQLITE_LOCK_PENDING], or
** <li> [SQLITE_LOCK_EXCLUSIVE].
** </ul>
-** xLock() increases the lock. xUnlock() decreases the lock.
+** xLock() upgrades the database file lock. In other words, xLock() moves the
+** database file lock in the direction NONE toward EXCLUSIVE. The argument to
+** xLock() is always one of SHARED, RESERVED, PENDING, or EXCLUSIVE, never
+** SQLITE_LOCK_NONE. If the database file lock is already at or above the
+** requested lock, then the call to xLock() is a no-op.
+** xUnlock() downgrades the database file lock to either SHARED or NONE.
+** If the lock is already at or below the requested lock state, then the call
+** to xUnlock() is a no-op.
** The xCheckReservedLock() method checks whether any database connection,
** either in this process or in some other process, is holding a RESERVED,
-** PENDING, or EXCLUSIVE lock on the file. It returns true
-** if such a lock exists and false otherwise.
+** PENDING, or EXCLUSIVE lock on the file. It returns, via its output
+** pointer parameter, true if such a lock exists and false otherwise.
**
** The xFileControl() method is a generic interface that allows custom
** VFS implementations to directly control an open file using the
@@ -761,6 +822,7 @@ struct sqlite3_file {
** <li> [SQLITE_IOCAP_POWERSAFE_OVERWRITE]
** <li> [SQLITE_IOCAP_IMMUTABLE]
** <li> [SQLITE_IOCAP_BATCH_ATOMIC]
+** <li> [SQLITE_IOCAP_SUBPAGE_READ]
** </ul>
**
** The SQLITE_IOCAP_ATOMIC property means that all writes of
@@ -821,9 +883,8 @@ struct sqlite3_io_methods {
** opcode causes the xFileControl method to write the current state of
** the lock (one of [SQLITE_LOCK_NONE], [SQLITE_LOCK_SHARED],
** [SQLITE_LOCK_RESERVED], [SQLITE_LOCK_PENDING], or [SQLITE_LOCK_EXCLUSIVE])
-** into an integer that the pArg argument points to. This capability
-** is used during testing and is only available when the SQLITE_TEST
-** compile-time option is used.
+** into an integer that the pArg argument points to.
+** This capability is only available if SQLite is compiled with [SQLITE_DEBUG].
**
** <li>[[SQLITE_FCNTL_SIZE_HINT]]
** The [SQLITE_FCNTL_SIZE_HINT] opcode is used by SQLite to give the VFS
@@ -1127,6 +1188,28 @@ struct sqlite3_io_methods {
** in wal mode after the client has finished copying pages from the wal
** file to the database file, but before the *-shm file is updated to
** record the fact that the pages have been checkpointed.
+**
+** <li>[[SQLITE_FCNTL_EXTERNAL_READER]]
+** The EXPERIMENTAL [SQLITE_FCNTL_EXTERNAL_READER] opcode is used to detect
+** whether or not there is a database client in another process with a wal-mode
+** transaction open on the database or not. It is only available on unix.The
+** (void*) argument passed with this file-control should be a pointer to a
+** value of type (int). The integer value is set to 1 if the database is a wal
+** mode database and there exists at least one client in another process that
+** currently has an SQL transaction open on the database. It is set to 0 if
+** the database is not a wal-mode db, or if there is no such connection in any
+** other process. This opcode cannot be used to detect transactions opened
+** by clients within the current process, only within other processes.
+**
+** <li>[[SQLITE_FCNTL_CKSM_FILE]]
+** The [SQLITE_FCNTL_CKSM_FILE] opcode is for use internally by the
+** [checksum VFS shim] only.
+**
+** <li>[[SQLITE_FCNTL_RESET_CACHE]]
+** If there is currently no transaction open on the database, and the
+** database is not a temp db, then the [SQLITE_FCNTL_RESET_CACHE] file-control
+** purges the contents of the in-memory page cache. If there is an open
+** transaction, or if the db is a temp-db, this opcode is a no-op, not an error.
** </ul>
*/
#define SQLITE_FCNTL_LOCKSTATE 1
@@ -1167,6 +1250,9 @@ struct sqlite3_io_methods {
#define SQLITE_FCNTL_CKPT_DONE 37
#define SQLITE_FCNTL_RESERVE_BYTES 38
#define SQLITE_FCNTL_CKPT_START 39
+#define SQLITE_FCNTL_EXTERNAL_READER 40
+#define SQLITE_FCNTL_CKSM_FILE 41
+#define SQLITE_FCNTL_RESET_CACHE 42
/* deprecated names */
#define SQLITE_GET_LOCKPROXYFILE SQLITE_FCNTL_GET_LOCKPROXYFILE
@@ -1197,6 +1283,26 @@ typedef struct sqlite3_mutex sqlite3_mutex;
typedef struct sqlite3_api_routines sqlite3_api_routines;
/*
+** CAPI3REF: File Name
+**
+** Type [sqlite3_filename] is used by SQLite to pass filenames to the
+** xOpen method of a [VFS]. It may be cast to (const char*) and treated
+** as a normal, nul-terminated, UTF-8 buffer containing the filename, but
+** may also be passed to special APIs such as:
+**
+** <ul>
+** <li> sqlite3_filename_database()
+** <li> sqlite3_filename_journal()
+** <li> sqlite3_filename_wal()
+** <li> sqlite3_uri_parameter()
+** <li> sqlite3_uri_boolean()
+** <li> sqlite3_uri_int64()
+** <li> sqlite3_uri_key()
+** </ul>
+*/
+typedef const char *sqlite3_filename;
+
+/*
** CAPI3REF: OS Interface Object
**
** An instance of the sqlite3_vfs object defines the interface between
@@ -1374,7 +1480,7 @@ struct sqlite3_vfs {
sqlite3_vfs *pNext; /* Next registered VFS */
const char *zName; /* Name of this virtual file system */
void *pAppData; /* Pointer to application-specific data */
- int (*xOpen)(sqlite3_vfs*, const char *zName, sqlite3_file*,
+ int (*xOpen)(sqlite3_vfs*, sqlite3_filename zName, sqlite3_file*,
int flags, int *pOutFlags);
int (*xDelete)(sqlite3_vfs*, const char *zName, int syncDir);
int (*xAccess)(sqlite3_vfs*, const char *zName, int flags, int *pResOut);
@@ -1561,20 +1667,23 @@ SQLITE_API int sqlite3_os_end(void);
** must ensure that no other SQLite interfaces are invoked by other
** threads while sqlite3_config() is running.</b>
**
-** The sqlite3_config() interface
-** may only be invoked prior to library initialization using
-** [sqlite3_initialize()] or after shutdown by [sqlite3_shutdown()].
-** ^If sqlite3_config() is called after [sqlite3_initialize()] and before
-** [sqlite3_shutdown()] then it will return SQLITE_MISUSE.
-** Note, however, that ^sqlite3_config() can be called as part of the
-** implementation of an application-defined [sqlite3_os_init()].
-**
** The first argument to sqlite3_config() is an integer
** [configuration option] that determines
** what property of SQLite is to be configured. Subsequent arguments
** vary depending on the [configuration option]
** in the first argument.
**
+** For most configuration options, the sqlite3_config() interface
+** may only be invoked prior to library initialization using
+** [sqlite3_initialize()] or after shutdown by [sqlite3_shutdown()].
+** The exceptional configuration options that may be invoked at any time
+** are called "anytime configuration options".
+** ^If sqlite3_config() is called after [sqlite3_initialize()] and before
+** [sqlite3_shutdown()] with a first argument that is not an anytime
+** configuration option, then the sqlite3_config() call will return SQLITE_MISUSE.
+** Note, however, that ^sqlite3_config() can be called as part of the
+** implementation of an application-defined [sqlite3_os_init()].
+**
** ^When a configuration option is set, sqlite3_config() returns [SQLITE_OK].
** ^If the option is unknown or SQLite is unable to set the option
** then this routine returns a non-zero [error code].
@@ -1682,6 +1791,23 @@ struct sqlite3_mem_methods {
** These constants are the available integer configuration options that
** can be passed as the first argument to the [sqlite3_config()] interface.
**
+** Most of the configuration options for sqlite3_config()
+** will only work if invoked prior to [sqlite3_initialize()] or after
+** [sqlite3_shutdown()]. The few exceptions to this rule are called
+** "anytime configuration options".
+** ^Calling [sqlite3_config()] with a first argument that is not an
+** anytime configuration option in between calls to [sqlite3_initialize()] and
+** [sqlite3_shutdown()] is a no-op that returns SQLITE_MISUSE.
+**
+** The set of anytime configuration options can change (by insertions
+** and/or deletions) from one release of SQLite to the next.
+** As of SQLite version 3.42.0, the complete set of anytime configuration
+** options is:
+** <ul>
+** <li> SQLITE_CONFIG_LOG
+** <li> SQLITE_CONFIG_PCACHE_HDRSZ
+** </ul>
+**
** New configuration options may be added in future releases of SQLite.
** Existing configuration options might be discontinued. Applications
** should check the return code from [sqlite3_config()] to make sure that
@@ -2012,7 +2138,7 @@ struct sqlite3_mem_methods {
** is stored in each sorted record and the required column values loaded
** from the database as records are returned in sorted order. The default
** value for this option is to never use this optimization. Specifying a
-** negative value for this option restores the default behaviour.
+** negative value for this option restores the default behavior.
** This option is only available if SQLite is compiled with the
** [SQLITE_ENABLE_SORTER_REFERENCES] compile-time option.
**
@@ -2026,30 +2152,46 @@ struct sqlite3_mem_methods {
** configuration setting is never used, then the default maximum is determined
** by the [SQLITE_MEMDB_DEFAULT_MAXSIZE] compile-time option. If that
** compile-time option is not set, then the default maximum is 1073741824.
+**
+** [[SQLITE_CONFIG_ROWID_IN_VIEW]]
+** <dt>SQLITE_CONFIG_ROWID_IN_VIEW
+** <dd>The SQLITE_CONFIG_ROWID_IN_VIEW option enables or disables the ability
+** for VIEWs to have a ROWID. The capability can only be enabled if SQLite is
+** compiled with -DSQLITE_ALLOW_ROWID_IN_VIEW, in which case the capability
+** defaults to on. This configuration option queries the current setting or
+** changes the setting to off or on. The argument is a pointer to an integer.
+** If that integer initially holds a value of 1, then the ability for VIEWs to
+** have ROWIDs is activated. If the integer initially holds zero, then the
+** ability is deactivated. Any other initial value for the integer leaves the
+** setting unchanged. After changes, if any, the integer is written with
+** a 1 or 0, if the ability for VIEWs to have ROWIDs is on or off. If SQLite
+** is compiled without -DSQLITE_ALLOW_ROWID_IN_VIEW (which is the usual and
+** recommended case) then the integer is always filled with zero, regardless
+** if its initial value.
** </dl>
*/
-#define SQLITE_CONFIG_SINGLETHREAD 1 /* nil */
-#define SQLITE_CONFIG_MULTITHREAD 2 /* nil */
-#define SQLITE_CONFIG_SERIALIZED 3 /* nil */
-#define SQLITE_CONFIG_MALLOC 4 /* sqlite3_mem_methods* */
-#define SQLITE_CONFIG_GETMALLOC 5 /* sqlite3_mem_methods* */
-#define SQLITE_CONFIG_SCRATCH 6 /* No longer used */
-#define SQLITE_CONFIG_PAGECACHE 7 /* void*, int sz, int N */
-#define SQLITE_CONFIG_HEAP 8 /* void*, int nByte, int min */
-#define SQLITE_CONFIG_MEMSTATUS 9 /* boolean */
-#define SQLITE_CONFIG_MUTEX 10 /* sqlite3_mutex_methods* */
-#define SQLITE_CONFIG_GETMUTEX 11 /* sqlite3_mutex_methods* */
-/* previously SQLITE_CONFIG_CHUNKALLOC 12 which is now unused. */
-#define SQLITE_CONFIG_LOOKASIDE 13 /* int int */
-#define SQLITE_CONFIG_PCACHE 14 /* no-op */
-#define SQLITE_CONFIG_GETPCACHE 15 /* no-op */
-#define SQLITE_CONFIG_LOG 16 /* xFunc, void* */
-#define SQLITE_CONFIG_URI 17 /* int */
-#define SQLITE_CONFIG_PCACHE2 18 /* sqlite3_pcache_methods2* */
-#define SQLITE_CONFIG_GETPCACHE2 19 /* sqlite3_pcache_methods2* */
+#define SQLITE_CONFIG_SINGLETHREAD 1 /* nil */
+#define SQLITE_CONFIG_MULTITHREAD 2 /* nil */
+#define SQLITE_CONFIG_SERIALIZED 3 /* nil */
+#define SQLITE_CONFIG_MALLOC 4 /* sqlite3_mem_methods* */
+#define SQLITE_CONFIG_GETMALLOC 5 /* sqlite3_mem_methods* */
+#define SQLITE_CONFIG_SCRATCH 6 /* No longer used */
+#define SQLITE_CONFIG_PAGECACHE 7 /* void*, int sz, int N */
+#define SQLITE_CONFIG_HEAP 8 /* void*, int nByte, int min */
+#define SQLITE_CONFIG_MEMSTATUS 9 /* boolean */
+#define SQLITE_CONFIG_MUTEX 10 /* sqlite3_mutex_methods* */
+#define SQLITE_CONFIG_GETMUTEX 11 /* sqlite3_mutex_methods* */
+/* previously SQLITE_CONFIG_CHUNKALLOC 12 which is now unused. */
+#define SQLITE_CONFIG_LOOKASIDE 13 /* int int */
+#define SQLITE_CONFIG_PCACHE 14 /* no-op */
+#define SQLITE_CONFIG_GETPCACHE 15 /* no-op */
+#define SQLITE_CONFIG_LOG 16 /* xFunc, void* */
+#define SQLITE_CONFIG_URI 17 /* int */
+#define SQLITE_CONFIG_PCACHE2 18 /* sqlite3_pcache_methods2* */
+#define SQLITE_CONFIG_GETPCACHE2 19 /* sqlite3_pcache_methods2* */
#define SQLITE_CONFIG_COVERING_INDEX_SCAN 20 /* int */
-#define SQLITE_CONFIG_SQLLOG 21 /* xSqllog, void* */
-#define SQLITE_CONFIG_MMAP_SIZE 22 /* sqlite3_int64, sqlite3_int64 */
+#define SQLITE_CONFIG_SQLLOG 21 /* xSqllog, void* */
+#define SQLITE_CONFIG_MMAP_SIZE 22 /* sqlite3_int64, sqlite3_int64 */
#define SQLITE_CONFIG_WIN32_HEAPSIZE 23 /* int nByte */
#define SQLITE_CONFIG_PCACHE_HDRSZ 24 /* int *psz */
#define SQLITE_CONFIG_PMASZ 25 /* unsigned int szPma */
@@ -2057,6 +2199,7 @@ struct sqlite3_mem_methods {
#define SQLITE_CONFIG_SMALL_MALLOC 27 /* boolean */
#define SQLITE_CONFIG_SORTERREF_SIZE 28 /* int nByte */
#define SQLITE_CONFIG_MEMDB_MAXSIZE 29 /* sqlite3_int64 */
+#define SQLITE_CONFIG_ROWID_IN_VIEW 30 /* int* */
/*
** CAPI3REF: Database Connection Configuration Options
@@ -2090,7 +2233,7 @@ struct sqlite3_mem_methods {
** configuration for a database connection can only be changed when that
** connection is not currently using lookaside memory, or in other words
** when the "current value" returned by
-** [sqlite3_db_status](D,[SQLITE_CONFIG_LOOKASIDE],...) is zero.
+** [sqlite3_db_status](D,[SQLITE_DBSTATUS_LOOKASIDE_USED],...) is zero.
** Any attempt to change the lookaside memory configuration when lookaside
** memory is in use leaves the configuration unchanged and returns
** [SQLITE_BUSY].)^</dd>
@@ -2115,7 +2258,13 @@ struct sqlite3_mem_methods {
** The second parameter is a pointer to an integer into which
** is written 0 or 1 to indicate whether triggers are disabled or enabled
** following this call. The second parameter may be a NULL pointer, in
-** which case the trigger setting is not reported back. </dd>
+** which case the trigger setting is not reported back.
+**
+** <p>Originally this option disabled all triggers. ^(However, since
+** SQLite version 3.35.0, TEMP triggers are still allowed even if
+** this option is off. So, in other words, this option now only disables
+** triggers in the main database schema or in the schemas of ATTACH-ed
+** databases.)^ </dd>
**
** [[SQLITE_DBCONFIG_ENABLE_VIEW]]
** <dt>SQLITE_DBCONFIG_ENABLE_VIEW</dt>
@@ -2126,7 +2275,13 @@ struct sqlite3_mem_methods {
** The second parameter is a pointer to an integer into which
** is written 0 or 1 to indicate whether views are disabled or enabled
** following this call. The second parameter may be a NULL pointer, in
-** which case the view setting is not reported back. </dd>
+** which case the view setting is not reported back.
+**
+** <p>Originally this option disabled all views. ^(However, since
+** SQLite version 3.35.0, TEMP views are still allowed even if
+** this option is off. So, in other words, this option now only disables
+** views in the main database schema or in the schemas of ATTACH-ed
+** databases.)^ </dd>
**
** [[SQLITE_DBCONFIG_ENABLE_FTS3_TOKENIZER]]
** <dt>SQLITE_DBCONFIG_ENABLE_FTS3_TOKENIZER</dt>
@@ -2175,7 +2330,7 @@ struct sqlite3_mem_methods {
** database handle, SQLite checks if this will mean that there are now no
** connections at all to the database. If so, it performs a checkpoint
** operation before closing the connection. This option may be used to
-** override this behaviour. The first parameter passed to this operation
+** override this behavior. The first parameter passed to this operation
** is an integer - positive to disable checkpoints-on-close, or zero (the
** default) to enable them, and negative to leave the setting unchanged.
** The second parameter is a pointer to an integer
@@ -2228,8 +2383,12 @@ struct sqlite3_mem_methods {
** <li> sqlite3_db_config(db, SQLITE_DBCONFIG_RESET_DATABASE, 0, 0);
** </ol>
** Because resetting a database is destructive and irreversible, the
-** process requires the use of this obscure API and multiple steps to help
-** ensure that it does not happen by accident.
+** process requires the use of this obscure API and multiple steps to
+** help ensure that it does not happen by accident. Because this
+** feature must be capable of resetting corrupt databases, and
+** shutting down virtual tables may require access to that corrupt
+** storage, the library must abandon any installed virtual tables
+** without calling their xDestroy() methods.
**
** [[SQLITE_DBCONFIG_DEFENSIVE]] <dt>SQLITE_DBCONFIG_DEFENSIVE</dt>
** <dd>The SQLITE_DBCONFIG_DEFENSIVE option activates or deactivates the
@@ -2240,6 +2399,7 @@ struct sqlite3_mem_methods {
** <ul>
** <li> The [PRAGMA writable_schema=ON] statement.
** <li> The [PRAGMA journal_mode=OFF] statement.
+** <li> The [PRAGMA schema_version=N] statement.
** <li> Writes to the [sqlite_dbpage] virtual table.
** <li> Direct writes to [shadow tables].
** </ul>
@@ -2267,7 +2427,7 @@ struct sqlite3_mem_methods {
** </dd>
**
** [[SQLITE_DBCONFIG_DQS_DML]]
-** <dt>SQLITE_DBCONFIG_DQS_DML</td>
+** <dt>SQLITE_DBCONFIG_DQS_DML</dt>
** <dd>The SQLITE_DBCONFIG_DQS_DML option activates or deactivates
** the legacy [double-quoted string literal] misfeature for DML statements
** only, that is DELETE, INSERT, SELECT, and UPDATE statements. The
@@ -2276,7 +2436,7 @@ struct sqlite3_mem_methods {
** </dd>
**
** [[SQLITE_DBCONFIG_DQS_DDL]]
-** <dt>SQLITE_DBCONFIG_DQS_DDL</td>
+** <dt>SQLITE_DBCONFIG_DQS_DDL</dt>
** <dd>The SQLITE_DBCONFIG_DQS option activates or deactivates
** the legacy [double-quoted string literal] misfeature for DDL statements,
** such as CREATE TABLE and CREATE INDEX. The
@@ -2285,7 +2445,7 @@ struct sqlite3_mem_methods {
** </dd>
**
** [[SQLITE_DBCONFIG_TRUSTED_SCHEMA]]
-** <dt>SQLITE_DBCONFIG_TRUSTED_SCHEMA</td>
+** <dt>SQLITE_DBCONFIG_TRUSTED_SCHEMA</dt>
** <dd>The SQLITE_DBCONFIG_TRUSTED_SCHEMA option tells SQLite to
** assume that database schemas are untainted by malicious content.
** When the SQLITE_DBCONFIG_TRUSTED_SCHEMA option is disabled, SQLite
@@ -2305,7 +2465,7 @@ struct sqlite3_mem_methods {
** </dd>
**
** [[SQLITE_DBCONFIG_LEGACY_FILE_FORMAT]]
-** <dt>SQLITE_DBCONFIG_LEGACY_FILE_FORMAT</td>
+** <dt>SQLITE_DBCONFIG_LEGACY_FILE_FORMAT</dt>
** <dd>The SQLITE_DBCONFIG_LEGACY_FILE_FORMAT option activates or deactivates
** the legacy file format flag. When activated, this flag causes all newly
** created database file to have a schema format version number (the 4-byte
@@ -2314,7 +2474,7 @@ struct sqlite3_mem_methods {
** any SQLite version back to 3.0.0 ([dateof:3.0.0]). Without this setting,
** newly created databases are generally not understandable by SQLite versions
** prior to 3.3.0 ([dateof:3.3.0]). As these words are written, there
-** is now scarcely any need to generated database files that are compatible
+** is now scarcely any need to generate database files that are compatible
** all the way back to version 3.0.0, and so this setting is of little
** practical use, but is provided so that SQLite can continue to claim the
** ability to generate new database files that are compatible with version
@@ -2323,8 +2483,40 @@ struct sqlite3_mem_methods {
** the [VACUUM] command will fail with an obscure error when attempting to
** process a table with generated columns and a descending index. This is
** not considered a bug since SQLite versions 3.3.0 and earlier do not support
-** either generated columns or decending indexes.
+** either generated columns or descending indexes.
** </dd>
+**
+** [[SQLITE_DBCONFIG_STMT_SCANSTATUS]]
+** <dt>SQLITE_DBCONFIG_STMT_SCANSTATUS</dt>
+** <dd>The SQLITE_DBCONFIG_STMT_SCANSTATUS option is only useful in
+** SQLITE_ENABLE_STMT_SCANSTATUS builds. In this case, it sets or clears
+** a flag that enables collection of the sqlite3_stmt_scanstatus_v2()
+** statistics. For statistics to be collected, the flag must be set on
+** the database handle both when the SQL statement is prepared and when it
+** is stepped. The flag is set (collection of statistics is enabled)
+** by default. This option takes two arguments: an integer and a pointer to
+** an integer.. The first argument is 1, 0, or -1 to enable, disable, or
+** leave unchanged the statement scanstatus option. If the second argument
+** is not NULL, then the value of the statement scanstatus setting after
+** processing the first argument is written into the integer that the second
+** argument points to.
+** </dd>
+**
+** [[SQLITE_DBCONFIG_REVERSE_SCANORDER]]
+** <dt>SQLITE_DBCONFIG_REVERSE_SCANORDER</dt>
+** <dd>The SQLITE_DBCONFIG_REVERSE_SCANORDER option changes the default order
+** in which tables and indexes are scanned so that the scans start at the end
+** and work toward the beginning rather than starting at the beginning and
+** working toward the end. Setting SQLITE_DBCONFIG_REVERSE_SCANORDER is the
+** same as setting [PRAGMA reverse_unordered_selects]. This option takes
+** two arguments which are an integer and a pointer to an integer. The first
+** argument is 1, 0, or -1 to enable, disable, or leave unchanged the
+** reverse scan order flag, respectively. If the second argument is not NULL,
+** then 0 or 1 is written into the integer that the second argument points to
+** depending on if the reverse scan order flag is set after processing the
+** first argument.
+** </dd>
+**
** </dl>
*/
#define SQLITE_DBCONFIG_MAINDBNAME 1000 /* const char* */
@@ -2345,7 +2537,9 @@ struct sqlite3_mem_methods {
#define SQLITE_DBCONFIG_ENABLE_VIEW 1015 /* int int* */
#define SQLITE_DBCONFIG_LEGACY_FILE_FORMAT 1016 /* int int* */
#define SQLITE_DBCONFIG_TRUSTED_SCHEMA 1017 /* int int* */
-#define SQLITE_DBCONFIG_MAX 1017 /* Largest DBCONFIG */
+#define SQLITE_DBCONFIG_STMT_SCANSTATUS 1018 /* int int* */
+#define SQLITE_DBCONFIG_REVERSE_SCANORDER 1019 /* int int* */
+#define SQLITE_DBCONFIG_MAX 1019 /* Largest DBCONFIG */
/*
** CAPI3REF: Enable Or Disable Extended Result Codes
@@ -2433,11 +2627,14 @@ SQLITE_API void sqlite3_set_last_insert_rowid(sqlite3*,sqlite3_int64);
** CAPI3REF: Count The Number Of Rows Modified
** METHOD: sqlite3
**
-** ^This function returns the number of rows modified, inserted or
+** ^These functions return the number of rows modified, inserted or
** deleted by the most recently completed INSERT, UPDATE or DELETE
** statement on the database connection specified by the only parameter.
-** ^Executing any other type of SQL statement does not modify the value
-** returned by this function.
+** The two functions are identical except for the type of the return value
+** and that if the number of rows modified by the most recent INSERT, UPDATE
+** or DELETE is greater than the maximum value supported by type "int", then
+** the return value of sqlite3_changes() is undefined. ^Executing any other
+** type of SQL statement does not modify the value returned by these functions.
**
** ^Only changes made directly by the INSERT, UPDATE or DELETE statement are
** considered - auxiliary changes caused by [CREATE TRIGGER | triggers],
@@ -2486,16 +2683,21 @@ SQLITE_API void sqlite3_set_last_insert_rowid(sqlite3*,sqlite3_int64);
** </ul>
*/
SQLITE_API int sqlite3_changes(sqlite3*);
+SQLITE_API sqlite3_int64 sqlite3_changes64(sqlite3*);
/*
** CAPI3REF: Total Number Of Rows Modified
** METHOD: sqlite3
**
-** ^This function returns the total number of rows inserted, modified or
+** ^These functions return the total number of rows inserted, modified or
** deleted by all [INSERT], [UPDATE] or [DELETE] statements completed
** since the database connection was opened, including those executed as
-** part of trigger programs. ^Executing any other type of SQL statement
-** does not affect the value returned by sqlite3_total_changes().
+** part of trigger programs. The two functions are identical except for the
+** type of the return value and that if the number of rows modified by the
+** connection exceeds the maximum value supported by type "int", then
+** the return value of sqlite3_total_changes() is undefined. ^Executing
+** any other type of SQL statement does not affect the value returned by
+** sqlite3_total_changes().
**
** ^Changes made as part of [foreign key actions] are included in the
** count, but those made as part of REPLACE constraint resolution are
@@ -2523,6 +2725,7 @@ SQLITE_API int sqlite3_changes(sqlite3*);
** </ul>
*/
SQLITE_API int sqlite3_total_changes(sqlite3*);
+SQLITE_API sqlite3_int64 sqlite3_total_changes64(sqlite3*);
/*
** CAPI3REF: Interrupt A Long-Running Query
@@ -2558,8 +2761,13 @@ SQLITE_API int sqlite3_total_changes(sqlite3*);
** ^A call to sqlite3_interrupt(D) that occurs when there are no running
** SQL statements is a no-op and has no effect on SQL statements
** that are started after the sqlite3_interrupt() call returns.
+**
+** ^The [sqlite3_is_interrupted(D)] interface can be used to determine whether
+** or not an interrupt is currently in effect for [database connection] D.
+** It returns 1 if an interrupt is currently in effect, or 0 otherwise.
*/
SQLITE_API void sqlite3_interrupt(sqlite3*);
+SQLITE_API int sqlite3_is_interrupted(sqlite3*);
/*
** CAPI3REF: Determine If An SQL Statement Is Complete
@@ -3106,8 +3314,8 @@ SQLITE_API int sqlite3_set_authorizer(
#define SQLITE_RECURSIVE 33 /* NULL NULL */
/*
-** CAPI3REF: Tracing And Profiling Functions
-** METHOD: sqlite3
+** CAPI3REF: Deprecated Tracing And Profiling Functions
+** DEPRECATED
**
** These routines are deprecated. Use the [sqlite3_trace_v2()] interface
** instead of the routines described here.
@@ -3177,8 +3385,8 @@ SQLITE_API SQLITE_DEPRECATED void *sqlite3_profile(sqlite3*,
** <dd>^An SQLITE_TRACE_PROFILE callback provides approximately the same
** information as is provided by the [sqlite3_profile()] callback.
** ^The P argument is a pointer to the [prepared statement] and the
-** X argument points to a 64-bit integer which is the estimated of
-** the number of nanosecond that the prepared statement took to run.
+** X argument points to a 64-bit integer which is approximately
+** the number of nanoseconds that the prepared statement took to run.
** ^The SQLITE_TRACE_PROFILE callback is invoked when the statement finishes.
**
** [[SQLITE_TRACE_ROW]] <dt>SQLITE_TRACE_ROW</dt>
@@ -3210,8 +3418,10 @@ SQLITE_API SQLITE_DEPRECATED void *sqlite3_profile(sqlite3*,
** M argument should be the bitwise OR-ed combination of
** zero or more [SQLITE_TRACE] constants.
**
-** ^Each call to either sqlite3_trace() or sqlite3_trace_v2() overrides
-** (cancels) any prior calls to sqlite3_trace() or sqlite3_trace_v2().
+** ^Each call to either sqlite3_trace(D,X,P) or sqlite3_trace_v2(D,M,X,P)
+** overrides (cancels) all prior calls to sqlite3_trace(D,X,P) or
+** sqlite3_trace_v2(D,M,X,P) for the [database connection] D. Each
+** database connection may have at most one trace callback.
**
** ^The X callback is invoked whenever any of the events identified by
** mask M occur. ^The integer return value from the callback is currently
@@ -3241,7 +3451,7 @@ SQLITE_API int sqlite3_trace_v2(
**
** ^The sqlite3_progress_handler(D,N,X,P) interface causes the callback
** function X to be invoked periodically during long running calls to
-** [sqlite3_exec()], [sqlite3_step()] and [sqlite3_get_table()] for
+** [sqlite3_step()] and [sqlite3_prepare()] and similar for
** database connection D. An example use for this
** interface is to keep a GUI updated during a large query.
**
@@ -3266,6 +3476,13 @@ SQLITE_API int sqlite3_trace_v2(
** Note that [sqlite3_prepare_v2()] and [sqlite3_step()] both modify their
** database connections for the meaning of "modify" in this paragraph.
**
+** The progress handler callback would originally only be invoked from the
+** bytecode engine. It still might be invoked during [sqlite3_prepare()]
+** and similar because those routines might force a reparse of the schema
+** which involves running the bytecode engine. However, beginning with
+** SQLite version 3.41.0, the progress handler callback might also be
+** invoked directly from [sqlite3_prepare()] while analyzing and generating
+** code for complex queries.
*/
SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
@@ -3302,13 +3519,18 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
**
** <dl>
** ^(<dt>[SQLITE_OPEN_READONLY]</dt>
-** <dd>The database is opened in read-only mode. If the database does not
-** already exist, an error is returned.</dd>)^
+** <dd>The database is opened in read-only mode. If the database does
+** not already exist, an error is returned.</dd>)^
**
** ^(<dt>[SQLITE_OPEN_READWRITE]</dt>
-** <dd>The database is opened for reading and writing if possible, or reading
-** only if the file is write protected by the operating system. In either
-** case the database must already exist, otherwise an error is returned.</dd>)^
+** <dd>The database is opened for reading and writing if possible, or
+** reading only if the file is write protected by the operating
+** system. In either case the database must already exist, otherwise
+** an error is returned. For historical reasons, if opening in
+** read-write mode fails due to OS-level permissions, an attempt is
+** made to open it in read-only mode. [sqlite3_db_readonly()] can be
+** used to determine whether the database is actually
+** read-write.</dd>)^
**
** ^(<dt>[SQLITE_OPEN_READWRITE] | [SQLITE_OPEN_CREATE]</dt>
** <dd>The database is opened for reading and writing, and is created if
@@ -3346,20 +3568,39 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
** <dd>The database is opened [shared cache] enabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
+** The [use of shared cache mode is discouraged] and hence shared cache
+** capabilities may be omitted from many builds of SQLite. In such cases,
+** this option is a no-op.
**
** ^(<dt>[SQLITE_OPEN_PRIVATECACHE]</dt>
** <dd>The database is opened [shared cache] disabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
+** [[OPEN_EXRESCODE]] ^(<dt>[SQLITE_OPEN_EXRESCODE]</dt>
+** <dd>The database connection comes up in "extended result code mode".
+** In other words, the database behaves as if
+** [sqlite3_extended_result_codes(db,1)] were called on the database
+** connection as soon as the connection is created. In addition to setting
+** the extended result code mode, this flag also causes [sqlite3_open_v2()]
+** to return an extended result code.</dd>
+**
** [[OPEN_NOFOLLOW]] ^(<dt>[SQLITE_OPEN_NOFOLLOW]</dt>
-** <dd>The database filename is not allowed to be a symbolic link</dd>
+** <dd>The database filename is not allowed to contain a symbolic link</dd>
** </dl>)^
**
** If the 3rd parameter to sqlite3_open_v2() is not one of the
** required combinations shown above optionally combined with other
** [SQLITE_OPEN_READONLY | SQLITE_OPEN_* bits]
-** then the behavior is undefined.
+** then the behavior is undefined. Historic versions of SQLite
+** have silently ignored surplus bits in the flags parameter to
+** sqlite3_open_v2(), however that behavior might not be carried through
+** into future versions of SQLite and so applications should not rely
+** upon it. Note in particular that the SQLITE_OPEN_EXCLUSIVE flag is a no-op
+** for sqlite3_open_v2(). The SQLITE_OPEN_EXCLUSIVE does *not* cause
+** the open to fail if the database already exists. The SQLITE_OPEN_EXCLUSIVE
+** flag is intended for use by the [sqlite3_vfs|VFS interface] only, and not
+** by sqlite3_open_v2().
**
** ^The fourth parameter to sqlite3_open_v2() is the name of the
** [sqlite3_vfs] object that defines the operating system interface that
@@ -3499,6 +3740,7 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
** that uses dot-files in place of posix advisory locking.
** <tr><td> file:data.db?mode=readonly <td>
** An error. "readonly" is not a valid option for the "mode" parameter.
+** Use "ro" instead: "file:data.db?mode=ro".
** </table>
**
** ^URI hexadecimal escape sequences (%HH) are supported within the path and
@@ -3548,7 +3790,7 @@ SQLITE_API int sqlite3_open_v2(
** as F) must be one of:
** <ul>
** <li> A database filename pointer created by the SQLite core and
-** passed into the xOpen() method of a VFS implemention, or
+** passed into the xOpen() method of a VFS implementation, or
** <li> A filename obtained from [sqlite3_db_filename()], or
** <li> A new filename constructed using [sqlite3_create_filename()].
** </ul>
@@ -3603,10 +3845,10 @@ SQLITE_API int sqlite3_open_v2(
**
** See the [URI filename] documentation for additional information.
*/
-SQLITE_API const char *sqlite3_uri_parameter(const char *zFilename, const char *zParam);
-SQLITE_API int sqlite3_uri_boolean(const char *zFile, const char *zParam, int bDefault);
-SQLITE_API sqlite3_int64 sqlite3_uri_int64(const char*, const char*, sqlite3_int64);
-SQLITE_API const char *sqlite3_uri_key(const char *zFilename, int N);
+SQLITE_API const char *sqlite3_uri_parameter(sqlite3_filename z, const char *zParam);
+SQLITE_API int sqlite3_uri_boolean(sqlite3_filename z, const char *zParam, int bDefault);
+SQLITE_API sqlite3_int64 sqlite3_uri_int64(sqlite3_filename, const char*, sqlite3_int64);
+SQLITE_API const char *sqlite3_uri_key(sqlite3_filename z, int N);
/*
** CAPI3REF: Translate filenames
@@ -3635,9 +3877,9 @@ SQLITE_API const char *sqlite3_uri_key(const char *zFilename, int N);
** return value from [sqlite3_db_filename()], then the result is
** undefined and is likely a memory access violation.
*/
-SQLITE_API const char *sqlite3_filename_database(const char*);
-SQLITE_API const char *sqlite3_filename_journal(const char*);
-SQLITE_API const char *sqlite3_filename_wal(const char*);
+SQLITE_API const char *sqlite3_filename_database(sqlite3_filename);
+SQLITE_API const char *sqlite3_filename_journal(sqlite3_filename);
+SQLITE_API const char *sqlite3_filename_wal(sqlite3_filename);
/*
** CAPI3REF: Database File Corresponding To A Journal
@@ -3661,7 +3903,7 @@ SQLITE_API sqlite3_file *sqlite3_database_file_object(const char*);
/*
** CAPI3REF: Create and Destroy VFS Filenames
**
-** These interfces are provided for use by [VFS shim] implementations and
+** These interfaces are provided for use by [VFS shim] implementations and
** are not useful outside of that context.
**
** The sqlite3_create_filename(D,J,W,N,P) allocates memory to hold a version of
@@ -3703,14 +3945,14 @@ SQLITE_API sqlite3_file *sqlite3_database_file_object(const char*);
** then the corresponding [sqlite3_module.xClose() method should also be
** invoked prior to calling sqlite3_free_filename(Y).
*/
-SQLITE_API char *sqlite3_create_filename(
+SQLITE_API sqlite3_filename sqlite3_create_filename(
const char *zDatabase,
const char *zJournal,
const char *zWal,
int nParam,
const char **azParam
);
-SQLITE_API void sqlite3_free_filename(char*);
+SQLITE_API void sqlite3_free_filename(sqlite3_filename);
/*
** CAPI3REF: Error Codes And Messages
@@ -3729,27 +3971,38 @@ SQLITE_API void sqlite3_free_filename(char*);
** sqlite3_extended_errcode() might change with each API call.
** Except, there are some interfaces that are guaranteed to never
** change the value of the error code. The error-code preserving
-** interfaces are:
+** interfaces include the following:
**
** <ul>
** <li> sqlite3_errcode()
** <li> sqlite3_extended_errcode()
** <li> sqlite3_errmsg()
** <li> sqlite3_errmsg16()
+** <li> sqlite3_error_offset()
** </ul>
**
** ^The sqlite3_errmsg() and sqlite3_errmsg16() return English-language
-** text that describes the error, as either UTF-8 or UTF-16 respectively.
+** text that describes the error, as either UTF-8 or UTF-16 respectively,
+** or NULL if no error message is available.
+** (See how SQLite handles [invalid UTF] for exceptions to this rule.)
** ^(Memory to hold the error message string is managed internally.
** The application does not need to worry about freeing the result.
** However, the error string might be overwritten or deallocated by
** subsequent calls to other SQLite interface functions.)^
**
-** ^The sqlite3_errstr() interface returns the English-language text
-** that describes the [result code], as UTF-8.
+** ^The sqlite3_errstr(E) interface returns the English-language text
+** that describes the [result code] E, as UTF-8, or NULL if E is not an
+** result code for which a text error message is available.
** ^(Memory to hold the error message string is managed internally
** and must not be freed by the application)^.
**
+** ^If the most recent error references a specific token in the input
+** SQL, the sqlite3_error_offset() interface returns the byte offset
+** of the start of that token. ^The byte offset returned by
+** sqlite3_error_offset() assumes that the input SQL is UTF8.
+** ^If the most recent error does not reference a specific token in the input
+** SQL, then the sqlite3_error_offset() function returns -1.
+**
** When the serialized [threading mode] is in use, it might be the
** case that a second error occurs on a separate thread in between
** the time of the first error and the call to these interfaces.
@@ -3769,6 +4022,7 @@ SQLITE_API int sqlite3_extended_errcode(sqlite3 *db);
SQLITE_API const char *sqlite3_errmsg(sqlite3*);
SQLITE_API const void *sqlite3_errmsg16(sqlite3*);
SQLITE_API const char *sqlite3_errstr(int);
+SQLITE_API int sqlite3_error_offset(sqlite3 *db);
/*
** CAPI3REF: Prepared Statement Object
@@ -3977,13 +4231,17 @@ SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal);
** and sqlite3_prepare16_v3() use UTF-16.
**
** ^If the nByte argument is negative, then zSql is read up to the
-** first zero terminator. ^If nByte is positive, then it is the
-** number of bytes read from zSql. ^If nByte is zero, then no prepared
+** first zero terminator. ^If nByte is positive, then it is the maximum
+** number of bytes read from zSql. When nByte is positive, zSql is read
+** up to the first zero terminator or until the nByte bytes have been read,
+** whichever comes first. ^If nByte is zero, then no prepared
** statement is generated.
** If the caller knows that the supplied string is nul-terminated, then
** there is a small performance advantage to passing an nByte parameter that
** is the number of bytes in the input string <i>including</i>
** the nul-terminator.
+** Note that nByte measure the length of the input in bytes, not
+** characters, even for the UTF-16 interfaces.
**
** ^If pzTail is not NULL then *pzTail is made to point to the first byte
** past the end of the first SQL statement in zSql. These routines only
@@ -4126,12 +4384,17 @@ SQLITE_API int sqlite3_prepare16_v3(
** are managed by SQLite and are automatically freed when the prepared
** statement is finalized.
** ^The string returned by sqlite3_expanded_sql(P), on the other hand,
-** is obtained from [sqlite3_malloc()] and must be free by the application
+** is obtained from [sqlite3_malloc()] and must be freed by the application
** by passing it to [sqlite3_free()].
+**
+** ^The sqlite3_normalized_sql() interface is only available if
+** the [SQLITE_ENABLE_NORMALIZE] compile-time option is defined.
*/
SQLITE_API const char *sqlite3_sql(sqlite3_stmt *pStmt);
SQLITE_API char *sqlite3_expanded_sql(sqlite3_stmt *pStmt);
+#ifdef SQLITE_ENABLE_NORMALIZE
SQLITE_API const char *sqlite3_normalized_sql(sqlite3_stmt *pStmt);
+#endif
/*
** CAPI3REF: Determine If An SQL Statement Writes The Database
@@ -4166,6 +4429,19 @@ SQLITE_API const char *sqlite3_normalized_sql(sqlite3_stmt *pStmt);
** [BEGIN] merely sets internal flags, but the [BEGIN|BEGIN IMMEDIATE] and
** [BEGIN|BEGIN EXCLUSIVE] commands do touch the database and so
** sqlite3_stmt_readonly() returns false for those commands.
+**
+** ^This routine returns false if there is any possibility that the
+** statement might change the database file. ^A false return does
+** not guarantee that the statement will change the database file.
+** ^For example, an UPDATE statement might have a WHERE clause that
+** makes it a no-op, but the sqlite3_stmt_readonly() result would still
+** be false. ^Similarly, a CREATE TABLE IF NOT EXISTS statement is a
+** read-only no-op if the table already exists, but
+** sqlite3_stmt_readonly() still returns false for such a statement.
+**
+** ^If prepared statement X is an [EXPLAIN] or [EXPLAIN QUERY PLAN]
+** statement, then sqlite3_stmt_readonly(X) returns the same value as
+** if the EXPLAIN or EXPLAIN QUERY PLAN prefix were omitted.
*/
SQLITE_API int sqlite3_stmt_readonly(sqlite3_stmt *pStmt);
@@ -4182,6 +4458,41 @@ SQLITE_API int sqlite3_stmt_readonly(sqlite3_stmt *pStmt);
SQLITE_API int sqlite3_stmt_isexplain(sqlite3_stmt *pStmt);
/*
+** CAPI3REF: Change The EXPLAIN Setting For A Prepared Statement
+** METHOD: sqlite3_stmt
+**
+** The sqlite3_stmt_explain(S,E) interface changes the EXPLAIN
+** setting for [prepared statement] S. If E is zero, then S becomes
+** a normal prepared statement. If E is 1, then S behaves as if
+** its SQL text began with "[EXPLAIN]". If E is 2, then S behaves as if
+** its SQL text began with "[EXPLAIN QUERY PLAN]".
+**
+** Calling sqlite3_stmt_explain(S,E) might cause S to be reprepared.
+** SQLite tries to avoid a reprepare, but a reprepare might be necessary
+** on the first transition into EXPLAIN or EXPLAIN QUERY PLAN mode.
+**
+** Because of the potential need to reprepare, a call to
+** sqlite3_stmt_explain(S,E) will fail with SQLITE_ERROR if S cannot be
+** reprepared because it was created using [sqlite3_prepare()] instead of
+** the newer [sqlite3_prepare_v2()] or [sqlite3_prepare_v3()] interfaces and
+** hence has no saved SQL text with which to reprepare.
+**
+** Changing the explain setting for a prepared statement does not change
+** the original SQL text for the statement. Hence, if the SQL text originally
+** began with EXPLAIN or EXPLAIN QUERY PLAN, but sqlite3_stmt_explain(S,0)
+** is called to convert the statement into an ordinary statement, the EXPLAIN
+** or EXPLAIN QUERY PLAN keywords will still appear in the sqlite3_sql(S)
+** output, even though the statement now acts like a normal SQL statement.
+**
+** This routine returns SQLITE_OK if the explain mode is successfully
+** changed, or an error code if the explain mode could not be changed.
+** The explain mode cannot be changed while a statement is active.
+** Hence, it is good practice to call [sqlite3_reset(S)]
+** immediately prior to calling sqlite3_stmt_explain(S,E).
+*/
+SQLITE_API int sqlite3_stmt_explain(sqlite3_stmt *pStmt, int eMode);
+
+/*
** CAPI3REF: Determine If A Prepared Statement Has Been Reset
** METHOD: sqlite3_stmt
**
@@ -4234,6 +4545,8 @@ SQLITE_API int sqlite3_stmt_busy(sqlite3_stmt*);
**
** ^The sqlite3_value objects that are passed as parameters into the
** implementation of [application-defined SQL functions] are protected.
+** ^The sqlite3_value objects returned by [sqlite3_vtab_rhs_value()]
+** are protected.
** ^The sqlite3_value object returned by
** [sqlite3_column_value()] is unprotected.
** Unprotected sqlite3_value objects may only be used as arguments
@@ -4335,18 +4648,22 @@ typedef struct sqlite3_context sqlite3_context;
** contain embedded NULs. The result of expressions involving strings
** with embedded NULs is undefined.
**
-** ^The fifth argument to the BLOB and string binding interfaces
-** is a destructor used to dispose of the BLOB or
-** string after SQLite has finished with it. ^The destructor is called
-** to dispose of the BLOB or string even if the call to the bind API fails,
-** except the destructor is not called if the third parameter is a NULL
-** pointer or the fourth parameter is negative.
-** ^If the fifth argument is
-** the special value [SQLITE_STATIC], then SQLite assumes that the
-** information is in static, unmanaged space and does not need to be freed.
-** ^If the fifth argument has the value [SQLITE_TRANSIENT], then
-** SQLite makes its own private copy of the data immediately, before
-** the sqlite3_bind_*() routine returns.
+** ^The fifth argument to the BLOB and string binding interfaces controls
+** or indicates the lifetime of the object referenced by the third parameter.
+** These three options exist:
+** ^ (1) A destructor to dispose of the BLOB or string after SQLite has finished
+** with it may be passed. ^It is called to dispose of the BLOB or string even
+** if the call to the bind API fails, except the destructor is not called if
+** the third parameter is a NULL pointer or the fourth parameter is negative.
+** ^ (2) The special constant, [SQLITE_STATIC], may be passed to indicate that
+** the application remains responsible for disposing of the object. ^In this
+** case, the object and the provided pointer to it must remain valid until
+** either the prepared statement is finalized or the same SQL parameter is
+** bound to something else, whichever occurs sooner.
+** ^ (3) The constant, [SQLITE_TRANSIENT], may be passed to indicate that the
+** object is to be copied prior to the return from sqlite3_bind_*(). ^The
+** object and pointer to it must remain valid until then. ^SQLite will then
+** manage the lifetime of its private copy.
**
** ^The sixth argument to sqlite3_bind_text64() must be one of
** [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE]
@@ -4851,6 +5168,10 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt);
** even empty strings, are always zero-terminated. ^The return
** value from sqlite3_column_blob() for a zero-length BLOB is a NULL pointer.
**
+** ^Strings returned by sqlite3_column_text16() always have the endianness
+** which is native to the platform, regardless of the text encoding set
+** for the database.
+**
** <b>Warning:</b> ^The object returned by [sqlite3_column_value()] is an
** [unprotected sqlite3_value] object. In a multithreaded environment,
** an unprotected sqlite3_value object may only be used safely with
@@ -4864,7 +5185,7 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt);
** [application-defined SQL functions] or [virtual tables], not within
** top-level application code.
**
-** The these routines may attempt to convert the datatype of the result.
+** These routines may attempt to convert the datatype of the result.
** ^For example, if the internal representation is FLOAT and a text result
** is requested, [sqlite3_snprintf()] is used internally to perform the
** conversion automatically. ^(The following table details the conversions
@@ -4889,7 +5210,7 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt);
** <tr><td> TEXT <td> BLOB <td> No change
** <tr><td> BLOB <td> INTEGER <td> [CAST] to INTEGER
** <tr><td> BLOB <td> FLOAT <td> [CAST] to REAL
-** <tr><td> BLOB <td> TEXT <td> Add a zero terminator if needed
+** <tr><td> BLOB <td> TEXT <td> [CAST] to TEXT, ensure zero terminator
** </table>
** </blockquote>)^
**
@@ -5013,20 +5334,33 @@ SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt);
** ^The [sqlite3_reset(S)] interface resets the [prepared statement] S
** back to the beginning of its program.
**
-** ^If the most recent call to [sqlite3_step(S)] for the
-** [prepared statement] S returned [SQLITE_ROW] or [SQLITE_DONE],
-** or if [sqlite3_step(S)] has never before been called on S,
-** then [sqlite3_reset(S)] returns [SQLITE_OK].
+** ^The return code from [sqlite3_reset(S)] indicates whether or not
+** the previous evaluation of prepared statement S completed successfully.
+** ^If [sqlite3_step(S)] has never before been called on S or if
+** [sqlite3_step(S)] has not been called since the previous call
+** to [sqlite3_reset(S)], then [sqlite3_reset(S)] will return
+** [SQLITE_OK].
**
** ^If the most recent call to [sqlite3_step(S)] for the
** [prepared statement] S indicated an error, then
** [sqlite3_reset(S)] returns an appropriate [error code].
+** ^The [sqlite3_reset(S)] interface might also return an [error code]
+** if there were no prior errors but the process of resetting
+** the prepared statement caused a new error. ^For example, if an
+** [INSERT] statement with a [RETURNING] clause is only stepped one time,
+** that one call to [sqlite3_step(S)] might return SQLITE_ROW but
+** the overall statement might still fail and the [sqlite3_reset(S)] call
+** might return SQLITE_BUSY if locking constraints prevent the
+** database change from committing. Therefore, it is important that
+** applications check the return code from [sqlite3_reset(S)] even if
+** no prior call to [sqlite3_step(S)] indicated a problem.
**
** ^The [sqlite3_reset(S)] interface does not change the values
** of any [sqlite3_bind_blob|bindings] on the [prepared statement] S.
*/
SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt);
+
/*
** CAPI3REF: Create Or Redefine SQL Functions
** KEYWORDS: {function creation routines}
@@ -5088,7 +5422,6 @@ SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt);
** within VIEWs, TRIGGERs, CHECK constraints, generated column expressions,
** index expressions, or the WHERE clause of partial indexes.
**
-** <span style="background-color:#ffff90;">
** For best security, the [SQLITE_DIRECTONLY] flag is recommended for
** all application-defined SQL functions that do not need to be
** used inside of triggers, view, CHECK constraints, or other elements of
@@ -5098,7 +5431,6 @@ SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt);
** a database file to include invocations of the function with parameters
** chosen by the attacker, which the application will then execute when
** the database file is opened and read.
-** </span>
**
** ^(The fifth parameter is an arbitrary pointer. The implementation of the
** function can gain access to this pointer using [sqlite3_user_data()].)^
@@ -5234,10 +5566,21 @@ SQLITE_API int sqlite3_create_window_function(
** from top-level SQL, and cannot be used in VIEWs or TRIGGERs nor in
** schema structures such as [CHECK constraints], [DEFAULT clauses],
** [expression indexes], [partial indexes], or [generated columns].
-** The SQLITE_DIRECTONLY flags is a security feature which is recommended
-** for all [application-defined SQL functions], and especially for functions
-** that have side-effects or that could potentially leak sensitive
-** information.
+** <p>
+** The SQLITE_DIRECTONLY flag is recommended for any
+** [application-defined SQL function]
+** that has side-effects or that could potentially leak sensitive information.
+** This will prevent attacks in which an application is tricked
+** into using a database file that has had its schema surreptitiously
+** modified to invoke the application-defined function in ways that are
+** harmful.
+** <p>
+** Some people say it is good practice to set SQLITE_DIRECTONLY on all
+** [application-defined SQL functions], regardless of whether or not they
+** are security sensitive, as doing so prevents those functions from being used
+** inside of the database schema, and thus ensures that the database
+** can be inspected and modified using generic tools (such as the [CLI])
+** that do not have access to the application-defined functions.
** </dd>
**
** [[SQLITE_INNOCUOUS]] <dt>SQLITE_INNOCUOUS</dt><dd>
@@ -5264,13 +5607,36 @@ SQLITE_API int sqlite3_create_window_function(
** </dd>
**
** [[SQLITE_SUBTYPE]] <dt>SQLITE_SUBTYPE</dt><dd>
-** The SQLITE_SUBTYPE flag indicates to SQLite that a function may call
+** The SQLITE_SUBTYPE flag indicates to SQLite that a function might call
** [sqlite3_value_subtype()] to inspect the sub-types of its arguments.
-** Specifying this flag makes no difference for scalar or aggregate user
-** functions. However, if it is not specified for a user-defined window
-** function, then any sub-types belonging to arguments passed to the window
-** function may be discarded before the window function is called (i.e.
-** sqlite3_value_subtype() will always return 0).
+** This flag instructs SQLite to omit some corner-case optimizations that
+** might disrupt the operation of the [sqlite3_value_subtype()] function,
+** causing it to return zero rather than the correct subtype().
+** All SQL functions that invoke [sqlite3_value_subtype()] should have this
+** property. If the SQLITE_SUBTYPE property is omitted, then the return
+** value from [sqlite3_value_subtype()] might sometimes be zero even though
+** a non-zero subtype was specified by the function argument expression.
+**
+** [[SQLITE_RESULT_SUBTYPE]] <dt>SQLITE_RESULT_SUBTYPE</dt><dd>
+** The SQLITE_RESULT_SUBTYPE flag indicates to SQLite that a function might call
+** [sqlite3_result_subtype()] to cause a sub-type to be associated with its
+** result.
+** Every function that invokes [sqlite3_result_subtype()] should have this
+** property. If it does not, then the call to [sqlite3_result_subtype()]
+** might become a no-op if the function is used as term in an
+** [expression index]. On the other hand, SQL functions that never invoke
+** [sqlite3_result_subtype()] should avoid setting this property, as the
+** purpose of this property is to disable certain optimizations that are
+** incompatible with subtypes.
+**
+** [[SQLITE_SELFORDER1]] <dt>SQLITE_SELFORDER1</dt><dd>
+** The SQLITE_SELFORDER1 flag indicates that the function is an aggregate
+** that internally orders the values provided to the first argument. The
+** ordered-set aggregate SQL notation with a single ORDER BY term can be
+** used to invoke this function. If the ordered-set aggregate notation is
+** used on a function that lacks this flag, then an error is raised. Note
+** that the ordered-set aggregate syntax is only available if SQLite is
+** built using the -DSQLITE_ENABLE_ORDERED_SET_AGGREGATES compile-time option.
** </dd>
** </dl>
*/
@@ -5278,6 +5644,8 @@ SQLITE_API int sqlite3_create_window_function(
#define SQLITE_DIRECTONLY 0x000080000
#define SQLITE_SUBTYPE 0x000100000
#define SQLITE_INNOCUOUS 0x000200000
+#define SQLITE_RESULT_SUBTYPE 0x001000000
+#define SQLITE_SELFORDER1 0x002000000
/*
** CAPI3REF: Deprecated Functions
@@ -5444,6 +5812,28 @@ SQLITE_API int sqlite3_value_nochange(sqlite3_value*);
SQLITE_API int sqlite3_value_frombind(sqlite3_value*);
/*
+** CAPI3REF: Report the internal text encoding state of an sqlite3_value object
+** METHOD: sqlite3_value
+**
+** ^(The sqlite3_value_encoding(X) interface returns one of [SQLITE_UTF8],
+** [SQLITE_UTF16BE], or [SQLITE_UTF16LE] according to the current text encoding
+** of the value X, assuming that X has type TEXT.)^ If sqlite3_value_type(X)
+** returns something other than SQLITE_TEXT, then the return value from
+** sqlite3_value_encoding(X) is meaningless. ^Calls to
+** [sqlite3_value_text(X)], [sqlite3_value_text16(X)], [sqlite3_value_text16be(X)],
+** [sqlite3_value_text16le(X)], [sqlite3_value_bytes(X)], or
+** [sqlite3_value_bytes16(X)] might change the encoding of the value X and
+** thus change the return from subsequent calls to sqlite3_value_encoding(X).
+**
+** This routine is intended for used by applications that test and validate
+** the SQLite implementation. This routine is inquiring about the opaque
+** internal state of an [sqlite3_value] object. Ordinary applications should
+** not need to know what the internal state of an sqlite3_value object is and
+** hence should not need to use this interface.
+*/
+SQLITE_API int sqlite3_value_encoding(sqlite3_value*);
+
+/*
** CAPI3REF: Finding The Subtype Of SQL Values
** METHOD: sqlite3_value
**
@@ -5452,6 +5842,12 @@ SQLITE_API int sqlite3_value_frombind(sqlite3_value*);
** information can be used to pass a limited amount of context from
** one SQL function to another. Use the [sqlite3_result_subtype()]
** routine to set the subtype for the return value of an SQL function.
+**
+** Every [application-defined SQL function] that invokes this interface
+** should include the [SQLITE_SUBTYPE] property in the text
+** encoding argument when the function is [sqlite3_create_function|registered].
+** If the [SQLITE_SUBTYPE] property is omitted, then sqlite3_value_subtype()
+** might return zero instead of the upstream subtype in some corner cases.
*/
SQLITE_API unsigned int sqlite3_value_subtype(sqlite3_value*);
@@ -5463,7 +5859,8 @@ SQLITE_API unsigned int sqlite3_value_subtype(sqlite3_value*);
** object D and returns a pointer to that copy. ^The [sqlite3_value] returned
** is a [protected sqlite3_value] object even if the input is not.
** ^The sqlite3_value_dup(V) interface returns NULL if V is NULL or if a
-** memory allocation fails.
+** memory allocation fails. ^If V is a [pointer value], then the result
+** of sqlite3_value_dup(V) is a NULL value.
**
** ^The sqlite3_value_free(V) interface frees an [sqlite3_value] object
** previously obtained from [sqlite3_value_dup()]. ^If V is a NULL pointer
@@ -5494,7 +5891,7 @@ SQLITE_API void sqlite3_value_free(sqlite3_value*);
**
** ^The sqlite3_aggregate_context(C,N) routine returns a NULL pointer
** when first called if N is less than or equal to zero or if a memory
-** allocate error occurs.
+** allocation error occurs.
**
** ^(The amount of space allocated by sqlite3_aggregate_context(C,N) is
** determined by the N parameter on first successful call. Changing the
@@ -5549,48 +5946,56 @@ SQLITE_API sqlite3 *sqlite3_context_db_handle(sqlite3_context*);
** METHOD: sqlite3_context
**
** These functions may be used by (non-aggregate) SQL functions to
-** associate metadata with argument values. If the same value is passed to
-** multiple invocations of the same SQL function during query execution, under
-** some circumstances the associated metadata may be preserved. An example
-** of where this might be useful is in a regular-expression matching
-** function. The compiled version of the regular expression can be stored as
-** metadata associated with the pattern string.
+** associate auxiliary data with argument values. If the same argument
+** value is passed to multiple invocations of the same SQL function during
+** query execution, under some circumstances the associated auxiliary data
+** might be preserved. An example of where this might be useful is in a
+** regular-expression matching function. The compiled version of the regular
+** expression can be stored as auxiliary data associated with the pattern string.
** Then as long as the pattern string remains the same,
** the compiled regular expression can be reused on multiple
** invocations of the same function.
**
-** ^The sqlite3_get_auxdata(C,N) interface returns a pointer to the metadata
+** ^The sqlite3_get_auxdata(C,N) interface returns a pointer to the auxiliary data
** associated by the sqlite3_set_auxdata(C,N,P,X) function with the Nth argument
** value to the application-defined function. ^N is zero for the left-most
-** function argument. ^If there is no metadata
+** function argument. ^If there is no auxiliary data
** associated with the function argument, the sqlite3_get_auxdata(C,N) interface
** returns a NULL pointer.
**
-** ^The sqlite3_set_auxdata(C,N,P,X) interface saves P as metadata for the N-th
-** argument of the application-defined function. ^Subsequent
+** ^The sqlite3_set_auxdata(C,N,P,X) interface saves P as auxiliary data for the
+** N-th argument of the application-defined function. ^Subsequent
** calls to sqlite3_get_auxdata(C,N) return P from the most recent
-** sqlite3_set_auxdata(C,N,P,X) call if the metadata is still valid or
-** NULL if the metadata has been discarded.
+** sqlite3_set_auxdata(C,N,P,X) call if the auxiliary data is still valid or
+** NULL if the auxiliary data has been discarded.
** ^After each call to sqlite3_set_auxdata(C,N,P,X) where X is not NULL,
** SQLite will invoke the destructor function X with parameter P exactly
-** once, when the metadata is discarded.
-** SQLite is free to discard the metadata at any time, including: <ul>
+** once, when the auxiliary data is discarded.
+** SQLite is free to discard the auxiliary data at any time, including: <ul>
** <li> ^(when the corresponding function parameter changes)^, or
** <li> ^(when [sqlite3_reset()] or [sqlite3_finalize()] is called for the
** SQL statement)^, or
** <li> ^(when sqlite3_set_auxdata() is invoked again on the same
** parameter)^, or
** <li> ^(during the original sqlite3_set_auxdata() call when a memory
-** allocation error occurs.)^ </ul>
+** allocation error occurs.)^
+** <li> ^(during the original sqlite3_set_auxdata() call if the function
+** is evaluated during query planning instead of during query execution,
+** as sometimes happens with [SQLITE_ENABLE_STAT4].)^ </ul>
**
-** Note the last bullet in particular. The destructor X in
+** Note the last two bullets in particular. The destructor X in
** sqlite3_set_auxdata(C,N,P,X) might be called immediately, before the
** sqlite3_set_auxdata() interface even returns. Hence sqlite3_set_auxdata()
** should be called near the end of the function implementation and the
** function implementation should not make any use of P after
-** sqlite3_set_auxdata() has been called.
-**
-** ^(In practice, metadata is preserved between function calls for
+** sqlite3_set_auxdata() has been called. Furthermore, a call to
+** sqlite3_get_auxdata() that occurs immediately after a corresponding call
+** to sqlite3_set_auxdata() might still return NULL if an out-of-memory
+** condition occurred during the sqlite3_set_auxdata() call or if the
+** function is being evaluated during query planning rather than during
+** query execution.
+**
+** ^(In practice, auxiliary data is preserved between function calls for
** function parameters that are compile-time constants, including literal
** values and [parameters] and expressions composed from the same.)^
**
@@ -5600,10 +6005,67 @@ SQLITE_API sqlite3 *sqlite3_context_db_handle(sqlite3_context*);
**
** These routines must be called from the same thread in which
** the SQL function is running.
+**
+** See also: [sqlite3_get_clientdata()] and [sqlite3_set_clientdata()].
*/
SQLITE_API void *sqlite3_get_auxdata(sqlite3_context*, int N);
SQLITE_API void sqlite3_set_auxdata(sqlite3_context*, int N, void*, void (*)(void*));
+/*
+** CAPI3REF: Database Connection Client Data
+** METHOD: sqlite3
+**
+** These functions are used to associate one or more named pointers
+** with a [database connection].
+** A call to sqlite3_set_clientdata(D,N,P,X) causes the pointer P
+** to be attached to [database connection] D using name N. Subsequent
+** calls to sqlite3_get_clientdata(D,N) will return a copy of pointer P
+** or a NULL pointer if there were no prior calls to
+** sqlite3_set_clientdata() with the same values of D and N.
+** Names are compared using strcmp() and are thus case sensitive.
+**
+** If P and X are both non-NULL, then the destructor X is invoked with
+** argument P on the first of the following occurrences:
+** <ul>
+** <li> An out-of-memory error occurs during the call to
+** sqlite3_set_clientdata() which attempts to register pointer P.
+** <li> A subsequent call to sqlite3_set_clientdata(D,N,P,X) is made
+** with the same D and N parameters.
+** <li> The database connection closes. SQLite does not make any guarantees
+** about the order in which destructors are called, only that all
+** destructors will be called exactly once at some point during the
+** database connection closing process.
+** </ul>
+**
+** SQLite does not do anything with client data other than invoke
+** destructors on the client data at the appropriate time. The intended
+** use for client data is to provide a mechanism for wrapper libraries
+** to store additional information about an SQLite database connection.
+**
+** There is no limit (other than available memory) on the number of different
+** client data pointers (with different names) that can be attached to a
+** single database connection. However, the implementation is optimized
+** for the case of having only one or two different client data names.
+** Applications and wrapper libraries are discouraged from using more than
+** one client data name each.
+**
+** There is no way to enumerate the client data pointers
+** associated with a database connection. The N parameter can be thought
+** of as a secret key such that only code that knows the secret key is able
+** to access the associated data.
+**
+** Security Warning: These interfaces should not be exposed in scripting
+** languages or in other circumstances where it might be possible for an
+** an attacker to invoke them. Any agent that can invoke these interfaces
+** can probably also take control of the process.
+**
+** Database connection client data is only available for SQLite
+** version 3.44.0 ([dateof:3.44.0]) and later.
+**
+** See also: [sqlite3_set_auxdata()] and [sqlite3_get_auxdata()].
+*/
+SQLITE_API void *sqlite3_get_clientdata(sqlite3*,const char*);
+SQLITE_API int sqlite3_set_clientdata(sqlite3*, const char*, void*, void(*)(void*));
/*
** CAPI3REF: Constants Defining Special Destructor Behavior
@@ -5699,9 +6161,10 @@ typedef void (*sqlite3_destructor_type)(void*);
** of [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE].
** ^SQLite takes the text result from the application from
** the 2nd parameter of the sqlite3_result_text* interfaces.
-** ^If the 3rd parameter to the sqlite3_result_text* interfaces
-** is negative, then SQLite takes result text from the 2nd parameter
-** through the first zero character.
+** ^If the 3rd parameter to any of the sqlite3_result_text* interfaces
+** other than sqlite3_result_text64() is negative, then SQLite computes
+** the string length itself by searching the 2nd parameter for the first
+** zero character.
** ^If the 3rd parameter to the sqlite3_result_text* interfaces
** is non-negative, then as many bytes (not characters) of the text
** pointed to by the 2nd parameter are taken as the application-defined
@@ -5804,6 +6267,20 @@ SQLITE_API int sqlite3_result_zeroblob64(sqlite3_context*, sqlite3_uint64 n);
** higher order bits are discarded.
** The number of subtype bytes preserved by SQLite might increase
** in future releases of SQLite.
+**
+** Every [application-defined SQL function] that invokes this interface
+** should include the [SQLITE_RESULT_SUBTYPE] property in its
+** text encoding argument when the SQL function is
+** [sqlite3_create_function|registered]. If the [SQLITE_RESULT_SUBTYPE]
+** property is omitted from the function that invokes sqlite3_result_subtype(),
+** then in some cases the sqlite3_result_subtype() might fail to set
+** the result subtype.
+**
+** If SQLite is compiled with -DSQLITE_STRICT_SUBTYPE=1, then any
+** SQL function that invokes the sqlite3_result_subtype() interface
+** and that does not have the SQLITE_RESULT_SUBTYPE property will raise
+** an error. Future versions of SQLite might enable -DSQLITE_STRICT_SUBTYPE=1
+** by default.
*/
SQLITE_API void sqlite3_result_subtype(sqlite3_context*,unsigned int);
@@ -5975,6 +6452,13 @@ SQLITE_API void sqlite3_activate_cerod(
** of the default VFS is not implemented correctly, or not implemented at
** all, then the behavior of sqlite3_sleep() may deviate from the description
** in the previous paragraphs.
+**
+** If a negative argument is passed to sqlite3_sleep() the results vary by
+** VFS and operating system. Some system treat a negative argument as an
+** instruction to sleep forever. Others understand it to mean do not sleep
+** at all. ^In SQLite version 3.42.0 and later, a negative
+** argument passed into sqlite3_sleep() is changed to zero before it is relayed
+** down into the xSleep method of the VFS.
*/
SQLITE_API int sqlite3_sleep(int);
@@ -6146,6 +6630,28 @@ SQLITE_API int sqlite3_get_autocommit(sqlite3*);
SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt*);
/*
+** CAPI3REF: Return The Schema Name For A Database Connection
+** METHOD: sqlite3
+**
+** ^The sqlite3_db_name(D,N) interface returns a pointer to the schema name
+** for the N-th database on database connection D, or a NULL pointer of N is
+** out of range. An N value of 0 means the main database file. An N of 1 is
+** the "temp" schema. Larger values of N correspond to various ATTACH-ed
+** databases.
+**
+** Space to hold the string that is returned by sqlite3_db_name() is managed
+** by SQLite itself. The string might be deallocated by any operation that
+** changes the schema, including [ATTACH] or [DETACH] or calls to
+** [sqlite3_serialize()] or [sqlite3_deserialize()], even operations that
+** occur on a different thread. Applications that need to
+** remember the string long-term should make their own copy. Applications that
+** are accessing the same database connection simultaneously on multiple
+** threads should mutex-protect calls to this API and should make their own
+** private copy of the result prior to releasing the mutex.
+*/
+SQLITE_API const char *sqlite3_db_name(sqlite3 *db, int N);
+
+/*
** CAPI3REF: Return The Filename For A Database Connection
** METHOD: sqlite3
**
@@ -6175,7 +6681,7 @@ SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt*);
** <li> [sqlite3_filename_wal()]
** </ul>
*/
-SQLITE_API const char *sqlite3_db_filename(sqlite3 *db, const char *zDbName);
+SQLITE_API sqlite3_filename sqlite3_db_filename(sqlite3 *db, const char *zDbName);
/*
** CAPI3REF: Determine if a database is read-only
@@ -6206,7 +6712,7 @@ SQLITE_API int sqlite3_db_readonly(sqlite3 *db, const char *zDbName);
SQLITE_API int sqlite3_txn_state(sqlite3*,const char *zSchema);
/*
-** CAPI3REF: Allowed return values from [sqlite3_txn_state()]
+** CAPI3REF: Allowed return values from sqlite3_txn_state()
** KEYWORDS: {transaction state}
**
** These constants define the current transaction state of a database file.
@@ -6305,6 +6811,72 @@ SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*);
SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);
/*
+** CAPI3REF: Autovacuum Compaction Amount Callback
+** METHOD: sqlite3
+**
+** ^The sqlite3_autovacuum_pages(D,C,P,X) interface registers a callback
+** function C that is invoked prior to each autovacuum of the database
+** file. ^The callback is passed a copy of the generic data pointer (P),
+** the schema-name of the attached database that is being autovacuumed,
+** the size of the database file in pages, the number of free pages,
+** and the number of bytes per page, respectively. The callback should
+** return the number of free pages that should be removed by the
+** autovacuum. ^If the callback returns zero, then no autovacuum happens.
+** ^If the value returned is greater than or equal to the number of
+** free pages, then a complete autovacuum happens.
+**
+** <p>^If there are multiple ATTACH-ed database files that are being
+** modified as part of a transaction commit, then the autovacuum pages
+** callback is invoked separately for each file.
+**
+** <p><b>The callback is not reentrant.</b> The callback function should
+** not attempt to invoke any other SQLite interface. If it does, bad
+** things may happen, including segmentation faults and corrupt database
+** files. The callback function should be a simple function that
+** does some arithmetic on its input parameters and returns a result.
+**
+** ^The X parameter to sqlite3_autovacuum_pages(D,C,P,X) is an optional
+** destructor for the P parameter. ^If X is not NULL, then X(P) is
+** invoked whenever the database connection closes or when the callback
+** is overwritten by another invocation of sqlite3_autovacuum_pages().
+**
+** <p>^There is only one autovacuum pages callback per database connection.
+** ^Each call to the sqlite3_autovacuum_pages() interface overrides all
+** previous invocations for that database connection. ^If the callback
+** argument (C) to sqlite3_autovacuum_pages(D,C,P,X) is a NULL pointer,
+** then the autovacuum steps callback is canceled. The return value
+** from sqlite3_autovacuum_pages() is normally SQLITE_OK, but might
+** be some other error code if something goes wrong. The current
+** implementation will only return SQLITE_OK or SQLITE_MISUSE, but other
+** return codes might be added in future releases.
+**
+** <p>If no autovacuum pages callback is specified (the usual case) or
+** a NULL pointer is provided for the callback,
+** then the default behavior is to vacuum all free pages. So, in other
+** words, the default behavior is the same as if the callback function
+** were something like this:
+**
+** <blockquote><pre>
+** &nbsp; unsigned int demonstration_autovac_pages_callback(
+** &nbsp; void *pClientData,
+** &nbsp; const char *zSchema,
+** &nbsp; unsigned int nDbPage,
+** &nbsp; unsigned int nFreePage,
+** &nbsp; unsigned int nBytePerPage
+** &nbsp; ){
+** &nbsp; return nFreePage;
+** &nbsp; }
+** </pre></blockquote>
+*/
+SQLITE_API int sqlite3_autovacuum_pages(
+ sqlite3 *db,
+ unsigned int(*)(void*,const char*,unsigned int,unsigned int,unsigned int),
+ void*,
+ void(*)(void*)
+);
+
+
+/*
** CAPI3REF: Data Change Notification Callbacks
** METHOD: sqlite3
**
@@ -6338,6 +6910,12 @@ SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);
** The exceptions defined in this paragraph might change in a future
** release of SQLite.
**
+** Whether the update hook is invoked before or after the
+** corresponding change is currently unspecified and may differ
+** depending on the type of change. Do not rely on the order of the
+** hook call with regards to the final result of the operation which
+** triggers the hook.
+**
** The update hook implementation must not do anything that will modify
** the database connection that invoked the update hook. Any actions
** to modify the database connection must be deferred until after the
@@ -6367,6 +6945,11 @@ SQLITE_API void *sqlite3_update_hook(
** to the same database. Sharing is enabled if the argument is true
** and disabled if the argument is false.)^
**
+** This interface is omitted if SQLite is compiled with
+** [-DSQLITE_OMIT_SHARED_CACHE]. The [-DSQLITE_OMIT_SHARED_CACHE]
+** compile-time option is recommended because the
+** [use of shared cache mode is discouraged].
+**
** ^Cache sharing is enabled and disabled for an entire process.
** This is a change as of SQLite [version 3.5.0] ([dateof:3.5.0]).
** In prior versions of SQLite,
@@ -6465,7 +7048,7 @@ SQLITE_API int sqlite3_db_release_memory(sqlite3*);
** ^The soft heap limit may not be greater than the hard heap limit.
** ^If the hard heap limit is enabled and if sqlite3_soft_heap_limit(N)
** is invoked with a value of N that is greater than the hard heap limit,
-** the the soft heap limit is set to the value of the hard heap limit.
+** the soft heap limit is set to the value of the hard heap limit.
** ^The soft heap limit is automatically enabled whenever the hard heap
** limit is enabled. ^When sqlite3_hard_heap_limit64(N) is invoked and
** the soft heap limit is outside the range of 1..N, then the soft heap
@@ -6727,15 +7310,6 @@ SQLITE_API int sqlite3_cancel_auto_extension(void(*xEntryPoint)(void));
SQLITE_API void sqlite3_reset_auto_extension(void);
/*
-** The interface to the virtual-table mechanism is currently considered
-** to be experimental. The interface might change in incompatible ways.
-** If this is a problem for you, do not use the interface at this time.
-**
-** When the virtual-table mechanism stabilizes, we will declare the
-** interface fixed, support it indefinitely, and remove this comment.
-*/
-
-/*
** Structures used by the virtual table interface
*/
typedef struct sqlite3_vtab sqlite3_vtab;
@@ -6795,6 +7369,10 @@ struct sqlite3_module {
/* The methods above are in versions 1 and 2 of the sqlite_module object.
** Those below are for version 3 and greater. */
int (*xShadowName)(const char*);
+ /* The methods above are in versions 1 through 3 of the sqlite_module object.
+ ** Those below are for version 4 and greater. */
+ int (*xIntegrity)(sqlite3_vtab *pVTab, const char *zSchema,
+ const char *zTabName, int mFlags, char **pzErr);
};
/*
@@ -6853,10 +7431,10 @@ struct sqlite3_module {
** when the omit flag is true there is no guarantee that the constraint will
** not be checked again using byte code.)^
**
-** ^The idxNum and idxPtr values are recorded and passed into the
+** ^The idxNum and idxStr values are recorded and passed into the
** [xFilter] method.
-** ^[sqlite3_free()] is used to free idxPtr if and only if
-** needToFreeIdxPtr is true.
+** ^[sqlite3_free()] is used to free idxStr if and only if
+** needToFreeIdxStr is true.
**
** ^The orderByConsumed means that output from [xFilter]/[xNext] will occur in
** the correct order to satisfy the ORDER BY clause so that no separate
@@ -6872,9 +7450,11 @@ struct sqlite3_module {
** will be returned by the strategy.
**
** The xBestIndex method may optionally populate the idxFlags field with a
-** mask of SQLITE_INDEX_SCAN_* flags. Currently there is only one such flag -
-** SQLITE_INDEX_SCAN_UNIQUE. If the xBestIndex method sets this flag, SQLite
-** assumes that the strategy may visit at most one row.
+** mask of SQLITE_INDEX_SCAN_* flags. One such flag is
+** [SQLITE_INDEX_SCAN_HEX], which if set causes the [EXPLAIN QUERY PLAN]
+** output to show the idxNum has hex instead of as decimal. Another flag is
+** SQLITE_INDEX_SCAN_UNIQUE, which if set indicates that the query plan will
+** return at most one row.
**
** Additionally, if xBestIndex sets the SQLITE_INDEX_SCAN_UNIQUE flag, then
** SQLite also assumes that if a call to the xUpdate() method is made as
@@ -6938,31 +7518,65 @@ struct sqlite3_index_info {
** [sqlite3_index_info].idxFlags field to some combination of
** these bits.
*/
-#define SQLITE_INDEX_SCAN_UNIQUE 1 /* Scan visits at most 1 row */
+#define SQLITE_INDEX_SCAN_UNIQUE 0x00000001 /* Scan visits at most 1 row */
+#define SQLITE_INDEX_SCAN_HEX 0x00000002 /* Display idxNum as hex */
+ /* in EXPLAIN QUERY PLAN */
/*
** CAPI3REF: Virtual Table Constraint Operator Codes
**
** These macros define the allowed values for the
** [sqlite3_index_info].aConstraint[].op field. Each value represents
-** an operator that is part of a constraint term in the wHERE clause of
+** an operator that is part of a constraint term in the WHERE clause of
** a query that uses a [virtual table].
-*/
-#define SQLITE_INDEX_CONSTRAINT_EQ 2
-#define SQLITE_INDEX_CONSTRAINT_GT 4
-#define SQLITE_INDEX_CONSTRAINT_LE 8
-#define SQLITE_INDEX_CONSTRAINT_LT 16
-#define SQLITE_INDEX_CONSTRAINT_GE 32
-#define SQLITE_INDEX_CONSTRAINT_MATCH 64
-#define SQLITE_INDEX_CONSTRAINT_LIKE 65
-#define SQLITE_INDEX_CONSTRAINT_GLOB 66
-#define SQLITE_INDEX_CONSTRAINT_REGEXP 67
-#define SQLITE_INDEX_CONSTRAINT_NE 68
-#define SQLITE_INDEX_CONSTRAINT_ISNOT 69
-#define SQLITE_INDEX_CONSTRAINT_ISNOTNULL 70
-#define SQLITE_INDEX_CONSTRAINT_ISNULL 71
-#define SQLITE_INDEX_CONSTRAINT_IS 72
-#define SQLITE_INDEX_CONSTRAINT_FUNCTION 150
+**
+** ^The left-hand operand of the operator is given by the corresponding
+** aConstraint[].iColumn field. ^An iColumn of -1 indicates the left-hand
+** operand is the rowid.
+** The SQLITE_INDEX_CONSTRAINT_LIMIT and SQLITE_INDEX_CONSTRAINT_OFFSET
+** operators have no left-hand operand, and so for those operators the
+** corresponding aConstraint[].iColumn is meaningless and should not be
+** used.
+**
+** All operator values from SQLITE_INDEX_CONSTRAINT_FUNCTION through
+** value 255 are reserved to represent functions that are overloaded
+** by the [xFindFunction|xFindFunction method] of the virtual table
+** implementation.
+**
+** The right-hand operands for each constraint might be accessible using
+** the [sqlite3_vtab_rhs_value()] interface. Usually the right-hand
+** operand is only available if it appears as a single constant literal
+** in the input SQL. If the right-hand operand is another column or an
+** expression (even a constant expression) or a parameter, then the
+** sqlite3_vtab_rhs_value() probably will not be able to extract it.
+** ^The SQLITE_INDEX_CONSTRAINT_ISNULL and
+** SQLITE_INDEX_CONSTRAINT_ISNOTNULL operators have no right-hand operand
+** and hence calls to sqlite3_vtab_rhs_value() for those operators will
+** always return SQLITE_NOTFOUND.
+**
+** The collating sequence to be used for comparison can be found using
+** the [sqlite3_vtab_collation()] interface. For most real-world virtual
+** tables, the collating sequence of constraints does not matter (for example
+** because the constraints are numeric) and so the sqlite3_vtab_collation()
+** interface is not commonly needed.
+*/
+#define SQLITE_INDEX_CONSTRAINT_EQ 2
+#define SQLITE_INDEX_CONSTRAINT_GT 4
+#define SQLITE_INDEX_CONSTRAINT_LE 8
+#define SQLITE_INDEX_CONSTRAINT_LT 16
+#define SQLITE_INDEX_CONSTRAINT_GE 32
+#define SQLITE_INDEX_CONSTRAINT_MATCH 64
+#define SQLITE_INDEX_CONSTRAINT_LIKE 65
+#define SQLITE_INDEX_CONSTRAINT_GLOB 66
+#define SQLITE_INDEX_CONSTRAINT_REGEXP 67
+#define SQLITE_INDEX_CONSTRAINT_NE 68
+#define SQLITE_INDEX_CONSTRAINT_ISNOT 69
+#define SQLITE_INDEX_CONSTRAINT_ISNOTNULL 70
+#define SQLITE_INDEX_CONSTRAINT_ISNULL 71
+#define SQLITE_INDEX_CONSTRAINT_IS 72
+#define SQLITE_INDEX_CONSTRAINT_LIMIT 73
+#define SQLITE_INDEX_CONSTRAINT_OFFSET 74
+#define SQLITE_INDEX_CONSTRAINT_FUNCTION 150
/*
** CAPI3REF: Register A Virtual Table Implementation
@@ -6991,7 +7605,7 @@ struct sqlite3_index_info {
** destructor.
**
** ^If the third parameter (the pointer to the sqlite3_module object) is
-** NULL then no new module is create and any existing modules with the
+** NULL then no new module is created and any existing modules with the
** same name are dropped.
**
** See also: [sqlite3_drop_modules()]
@@ -7104,16 +7718,6 @@ SQLITE_API int sqlite3_declare_vtab(sqlite3*, const char *zSQL);
SQLITE_API int sqlite3_overload_function(sqlite3*, const char *zFuncName, int nArg);
/*
-** The interface to the virtual-table mechanism defined above (back up
-** to a comment remarkably similar to this one) is currently considered
-** to be experimental. The interface might change in incompatible ways.
-** If this is a problem for you, do not use the interface at this time.
-**
-** When the virtual-table mechanism stabilizes, we will declare the
-** interface fixed, support it indefinitely, and remove this comment.
-*/
-
-/*
** CAPI3REF: A Handle To An Open BLOB
** KEYWORDS: {BLOB handle} {BLOB handles}
**
@@ -7260,7 +7864,7 @@ SQLITE_API int sqlite3_blob_reopen(sqlite3_blob *, sqlite3_int64);
** code is returned and the transaction rolled back.
**
** Calling this function with an argument that is not a NULL pointer or an
-** open blob handle results in undefined behaviour. ^Calling this routine
+** open blob handle results in undefined behavior. ^Calling this routine
** with a null pointer (such as would be returned by a failed call to
** [sqlite3_blob_open()]) is a harmless no-op. ^Otherwise, if this function
** is passed a valid open blob handle, the values returned by the
@@ -7487,18 +8091,20 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*);
**
** ^(Some systems (for example, Windows 95) do not support the operation
** implemented by sqlite3_mutex_try(). On those systems, sqlite3_mutex_try()
-** will always return SQLITE_BUSY. The SQLite core only ever uses
-** sqlite3_mutex_try() as an optimization so this is acceptable
-** behavior.)^
+** will always return SQLITE_BUSY. In most cases the SQLite core only uses
+** sqlite3_mutex_try() as an optimization, so this is acceptable
+** behavior. The exceptions are unix builds that set the
+** SQLITE_ENABLE_SETLK_TIMEOUT build option. In that case a working
+** sqlite3_mutex_try() is required.)^
**
** ^The sqlite3_mutex_leave() routine exits a mutex that was
** previously entered by the same thread. The behavior
** is undefined if the mutex is not currently entered by the
** calling thread or is not currently allocated.
**
-** ^If the argument to sqlite3_mutex_enter(), sqlite3_mutex_try(), or
-** sqlite3_mutex_leave() is a NULL pointer, then all three routines
-** behave as no-ops.
+** ^If the argument to sqlite3_mutex_enter(), sqlite3_mutex_try(),
+** sqlite3_mutex_leave(), or sqlite3_mutex_free() is a NULL pointer,
+** then any of the four routines behaves as a no-op.
**
** See also: [sqlite3_mutex_held()] and [sqlite3_mutex_notheld()].
*/
@@ -7740,6 +8346,7 @@ SQLITE_API int sqlite3_test_control(int op, ...);
#define SQLITE_TESTCTRL_PRNG_SAVE 5
#define SQLITE_TESTCTRL_PRNG_RESTORE 6
#define SQLITE_TESTCTRL_PRNG_RESET 7 /* NOT USED */
+#define SQLITE_TESTCTRL_FK_NO_ACTION 7
#define SQLITE_TESTCTRL_BITVEC_TEST 8
#define SQLITE_TESTCTRL_FAULT_INSTALL 9
#define SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS 10
@@ -7747,8 +8354,10 @@ SQLITE_API int sqlite3_test_control(int op, ...);
#define SQLITE_TESTCTRL_ASSERT 12
#define SQLITE_TESTCTRL_ALWAYS 13
#define SQLITE_TESTCTRL_RESERVE 14 /* NOT USED */
+#define SQLITE_TESTCTRL_JSON_SELFCHECK 14
#define SQLITE_TESTCTRL_OPTIMIZATIONS 15
#define SQLITE_TESTCTRL_ISKEYWORD 16 /* NOT USED */
+#define SQLITE_TESTCTRL_GETOPT 16
#define SQLITE_TESTCTRL_SCRATCHMALLOC 17 /* NOT USED */
#define SQLITE_TESTCTRL_INTERNAL_FUNCTIONS 17
#define SQLITE_TESTCTRL_LOCALTIME_FAULT 18
@@ -7765,7 +8374,11 @@ SQLITE_API int sqlite3_test_control(int op, ...);
#define SQLITE_TESTCTRL_PRNG_SEED 28
#define SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS 29
#define SQLITE_TESTCTRL_SEEK_COUNT 30
-#define SQLITE_TESTCTRL_LAST 30 /* Largest TESTCTRL */
+#define SQLITE_TESTCTRL_TRACEFLAGS 31
+#define SQLITE_TESTCTRL_TUNE 32
+#define SQLITE_TESTCTRL_LOGEST 33
+#define SQLITE_TESTCTRL_USELONGDOUBLE 34 /* NOT USED */
+#define SQLITE_TESTCTRL_LAST 34 /* Largest TESTCTRL */
/*
** CAPI3REF: SQL Keyword Checking
@@ -7778,7 +8391,7 @@ SQLITE_API int sqlite3_test_control(int op, ...);
** The sqlite3_keyword_count() interface returns the number of distinct
** keywords understood by SQLite.
**
-** The sqlite3_keyword_name(N,Z,L) interface finds the N-th keyword and
+** The sqlite3_keyword_name(N,Z,L) interface finds the 0-based N-th keyword and
** makes *Z point to that keyword expressed as UTF8 and writes the number
** of bytes in the keyword into *L. The string that *Z points to is not
** zero-terminated. The sqlite3_keyword_name(N,Z,L) routine returns
@@ -8288,6 +8901,16 @@ SQLITE_API int sqlite3_stmt_status(sqlite3_stmt*, int op,int resetFlg);
** The counter is incremented on the first [sqlite3_step()] call of each
** cycle.
**
+** [[SQLITE_STMTSTATUS_FILTER_MISS]]
+** [[SQLITE_STMTSTATUS_FILTER HIT]]
+** <dt>SQLITE_STMTSTATUS_FILTER_HIT<br>
+** SQLITE_STMTSTATUS_FILTER_MISS</dt>
+** <dd>^SQLITE_STMTSTATUS_FILTER_HIT is the number of times that a join
+** step was bypassed because a Bloom filter returned not-found. The
+** corresponding SQLITE_STMTSTATUS_FILTER_MISS value is the number of
+** times that the Bloom filter returned a find, and thus the join step
+** had to be processed as normal.
+**
** [[SQLITE_STMTSTATUS_MEMUSED]] <dt>SQLITE_STMTSTATUS_MEMUSED</dt>
** <dd>^This is the approximate number of bytes of heap memory
** used to store the prepared statement. ^This value is not actually
@@ -8302,6 +8925,8 @@ SQLITE_API int sqlite3_stmt_status(sqlite3_stmt*, int op,int resetFlg);
#define SQLITE_STMTSTATUS_VM_STEP 4
#define SQLITE_STMTSTATUS_REPREPARE 5
#define SQLITE_STMTSTATUS_RUN 6
+#define SQLITE_STMTSTATUS_FILTER_MISS 7
+#define SQLITE_STMTSTATUS_FILTER_HIT 8
#define SQLITE_STMTSTATUS_MEMUSED 99
/*
@@ -8713,7 +9338,7 @@ typedef struct sqlite3_backup sqlite3_backup;
** if the application incorrectly accesses the destination [database connection]
** and so no error code is reported, but the operations may malfunction
** nevertheless. Use of the destination database connection while a
-** backup is in progress might also also cause a mutex deadlock.
+** backup is in progress might also cause a mutex deadlock.
**
** If running in [shared cache mode], the application must
** guarantee that the shared cache used by the destination database
@@ -8728,6 +9353,16 @@ typedef struct sqlite3_backup sqlite3_backup;
** APIs are not strictly speaking threadsafe. If they are invoked at the
** same time as another thread is invoking sqlite3_backup_step() it is
** possible that they return invalid values.
+**
+** <b>Alternatives To Using The Backup API</b>
+**
+** Other techniques for safely creating a consistent backup of an SQLite
+** database include:
+**
+** <ul>
+** <li> The [VACUUM INTO] command.
+** <li> The [sqlite3_rsync] utility program.
+** </ul>
*/
SQLITE_API sqlite3_backup *sqlite3_backup_init(
sqlite3 *pDest, /* Destination database handle */
@@ -8965,8 +9600,9 @@ SQLITE_API void sqlite3_log(int iErrCode, const char *zFormat, ...);
**
** A single database handle may have at most a single write-ahead log callback
** registered at one time. ^Calling [sqlite3_wal_hook()] replaces any
-** previously registered write-ahead log callback. ^Note that the
-** [sqlite3_wal_autocheckpoint()] interface and the
+** previously registered write-ahead log callback. ^The return value is
+** a copy of the third parameter from the previous call, if any, or 0.
+** ^Note that the [sqlite3_wal_autocheckpoint()] interface and the
** [wal_autocheckpoint pragma] both invoke [sqlite3_wal_hook()] and will
** overwrite any prior [sqlite3_wal_hook()] settings.
*/
@@ -9140,7 +9776,7 @@ SQLITE_API int sqlite3_wal_checkpoint_v2(
*/
#define SQLITE_CHECKPOINT_PASSIVE 0 /* Do as much as possible w/o blocking */
#define SQLITE_CHECKPOINT_FULL 1 /* Wait for writers, then checkpoint */
-#define SQLITE_CHECKPOINT_RESTART 2 /* Like FULL but wait for for readers */
+#define SQLITE_CHECKPOINT_RESTART 2 /* Like FULL but wait for readers */
#define SQLITE_CHECKPOINT_TRUNCATE 3 /* Like RESTART but also truncate WAL */
/*
@@ -9208,7 +9844,7 @@ SQLITE_API int sqlite3_vtab_config(sqlite3*, int op, ...);
** [[SQLITE_VTAB_DIRECTONLY]]<dt>SQLITE_VTAB_DIRECTONLY</dt>
** <dd>Calls of the form
** [sqlite3_vtab_config](db,SQLITE_VTAB_DIRECTONLY) from within the
-** the [xConnect] or [xCreate] methods of a [virtual table] implmentation
+** the [xConnect] or [xCreate] methods of a [virtual table] implementation
** prohibits that virtual table from being used from within triggers and
** views.
** </dd>
@@ -9216,18 +9852,28 @@ SQLITE_API int sqlite3_vtab_config(sqlite3*, int op, ...);
** [[SQLITE_VTAB_INNOCUOUS]]<dt>SQLITE_VTAB_INNOCUOUS</dt>
** <dd>Calls of the form
** [sqlite3_vtab_config](db,SQLITE_VTAB_INNOCUOUS) from within the
-** the [xConnect] or [xCreate] methods of a [virtual table] implmentation
+** the [xConnect] or [xCreate] methods of a [virtual table] implementation
** identify that virtual table as being safe to use from within triggers
** and views. Conceptually, the SQLITE_VTAB_INNOCUOUS tag means that the
** virtual table can do no serious harm even if it is controlled by a
** malicious hacker. Developers should avoid setting the SQLITE_VTAB_INNOCUOUS
** flag unless absolutely necessary.
** </dd>
+**
+** [[SQLITE_VTAB_USES_ALL_SCHEMAS]]<dt>SQLITE_VTAB_USES_ALL_SCHEMAS</dt>
+** <dd>Calls of the form
+** [sqlite3_vtab_config](db,SQLITE_VTAB_USES_ALL_SCHEMA) from within the
+** the [xConnect] or [xCreate] methods of a [virtual table] implementation
+** instruct the query planner to begin at least a read transaction on
+** all schemas ("main", "temp", and any ATTACH-ed databases) whenever the
+** virtual table is used.
+** </dd>
** </dl>
*/
#define SQLITE_VTAB_CONSTRAINT_SUPPORT 1
#define SQLITE_VTAB_INNOCUOUS 2
#define SQLITE_VTAB_DIRECTONLY 3
+#define SQLITE_VTAB_USES_ALL_SCHEMAS 4
/*
** CAPI3REF: Determine The Virtual Table Conflict Policy
@@ -9269,18 +9915,295 @@ SQLITE_API int sqlite3_vtab_nochange(sqlite3_context*);
/*
** CAPI3REF: Determine The Collation For a Virtual Table Constraint
+** METHOD: sqlite3_index_info
**
** This function may only be called from within a call to the [xBestIndex]
-** method of a [virtual table].
+** method of a [virtual table]. This function returns a pointer to a string
+** that is the name of the appropriate collation sequence to use for text
+** comparisons on the constraint identified by its arguments.
+**
+** The first argument must be the pointer to the [sqlite3_index_info] object
+** that is the first parameter to the xBestIndex() method. The second argument
+** must be an index into the aConstraint[] array belonging to the
+** sqlite3_index_info structure passed to xBestIndex.
**
-** The first argument must be the sqlite3_index_info object that is the
-** first parameter to the xBestIndex() method. The second argument must be
-** an index into the aConstraint[] array belonging to the sqlite3_index_info
-** structure passed to xBestIndex. This function returns a pointer to a buffer
-** containing the name of the collation sequence for the corresponding
-** constraint.
+** Important:
+** The first parameter must be the same pointer that is passed into the
+** xBestMethod() method. The first parameter may not be a pointer to a
+** different [sqlite3_index_info] object, even an exact copy.
+**
+** The return value is computed as follows:
+**
+** <ol>
+** <li><p> If the constraint comes from a WHERE clause expression that contains
+** a [COLLATE operator], then the name of the collation specified by
+** that COLLATE operator is returned.
+** <li><p> If there is no COLLATE operator, but the column that is the subject
+** of the constraint specifies an alternative collating sequence via
+** a [COLLATE clause] on the column definition within the CREATE TABLE
+** statement that was passed into [sqlite3_declare_vtab()], then the
+** name of that alternative collating sequence is returned.
+** <li><p> Otherwise, "BINARY" is returned.
+** </ol>
*/
-SQLITE_API SQLITE_EXPERIMENTAL const char *sqlite3_vtab_collation(sqlite3_index_info*,int);
+SQLITE_API const char *sqlite3_vtab_collation(sqlite3_index_info*,int);
+
+/*
+** CAPI3REF: Determine if a virtual table query is DISTINCT
+** METHOD: sqlite3_index_info
+**
+** This API may only be used from within an [xBestIndex|xBestIndex method]
+** of a [virtual table] implementation. The result of calling this
+** interface from outside of xBestIndex() is undefined and probably harmful.
+**
+** ^The sqlite3_vtab_distinct() interface returns an integer between 0 and
+** 3. The integer returned by sqlite3_vtab_distinct()
+** gives the virtual table additional information about how the query
+** planner wants the output to be ordered. As long as the virtual table
+** can meet the ordering requirements of the query planner, it may set
+** the "orderByConsumed" flag.
+**
+** <ol><li value="0"><p>
+** ^If the sqlite3_vtab_distinct() interface returns 0, that means
+** that the query planner needs the virtual table to return all rows in the
+** sort order defined by the "nOrderBy" and "aOrderBy" fields of the
+** [sqlite3_index_info] object. This is the default expectation. If the
+** virtual table outputs all rows in sorted order, then it is always safe for
+** the xBestIndex method to set the "orderByConsumed" flag, regardless of
+** the return value from sqlite3_vtab_distinct().
+** <li value="1"><p>
+** ^(If the sqlite3_vtab_distinct() interface returns 1, that means
+** that the query planner does not need the rows to be returned in sorted order
+** as long as all rows with the same values in all columns identified by the
+** "aOrderBy" field are adjacent.)^ This mode is used when the query planner
+** is doing a GROUP BY.
+** <li value="2"><p>
+** ^(If the sqlite3_vtab_distinct() interface returns 2, that means
+** that the query planner does not need the rows returned in any particular
+** order, as long as rows with the same values in all columns identified
+** by "aOrderBy" are adjacent.)^ ^(Furthermore, when two or more rows
+** contain the same values for all columns identified by "colUsed", all but
+** one such row may optionally be omitted from the result.)^
+** The virtual table is not required to omit rows that are duplicates
+** over the "colUsed" columns, but if the virtual table can do that without
+** too much extra effort, it could potentially help the query to run faster.
+** This mode is used for a DISTINCT query.
+** <li value="3"><p>
+** ^(If the sqlite3_vtab_distinct() interface returns 3, that means the
+** virtual table must return rows in the order defined by "aOrderBy" as
+** if the sqlite3_vtab_distinct() interface had returned 0. However if
+** two or more rows in the result have the same values for all columns
+** identified by "colUsed", then all but one such row may optionally be
+** omitted.)^ Like when the return value is 2, the virtual table
+** is not required to omit rows that are duplicates over the "colUsed"
+** columns, but if the virtual table can do that without
+** too much extra effort, it could potentially help the query to run faster.
+** This mode is used for queries
+** that have both DISTINCT and ORDER BY clauses.
+** </ol>
+**
+** <p>The following table summarizes the conditions under which the
+** virtual table is allowed to set the "orderByConsumed" flag based on
+** the value returned by sqlite3_vtab_distinct(). This table is a
+** restatement of the previous four paragraphs:
+**
+** <table border=1 cellspacing=0 cellpadding=10 width="90%">
+** <tr>
+** <td valign="top">sqlite3_vtab_distinct() return value
+** <td valign="top">Rows are returned in aOrderBy order
+** <td valign="top">Rows with the same value in all aOrderBy columns are adjacent
+** <td valign="top">Duplicates over all colUsed columns may be omitted
+** <tr><td>0<td>yes<td>yes<td>no
+** <tr><td>1<td>no<td>yes<td>no
+** <tr><td>2<td>no<td>yes<td>yes
+** <tr><td>3<td>yes<td>yes<td>yes
+** </table>
+**
+** ^For the purposes of comparing virtual table output values to see if the
+** values are same value for sorting purposes, two NULL values are considered
+** to be the same. In other words, the comparison operator is "IS"
+** (or "IS NOT DISTINCT FROM") and not "==".
+**
+** If a virtual table implementation is unable to meet the requirements
+** specified above, then it must not set the "orderByConsumed" flag in the
+** [sqlite3_index_info] object or an incorrect answer may result.
+**
+** ^A virtual table implementation is always free to return rows in any order
+** it wants, as long as the "orderByConsumed" flag is not set. ^When the
+** the "orderByConsumed" flag is unset, the query planner will add extra
+** [bytecode] to ensure that the final results returned by the SQL query are
+** ordered correctly. The use of the "orderByConsumed" flag and the
+** sqlite3_vtab_distinct() interface is merely an optimization. ^Careful
+** use of the sqlite3_vtab_distinct() interface and the "orderByConsumed"
+** flag might help queries against a virtual table to run faster. Being
+** overly aggressive and setting the "orderByConsumed" flag when it is not
+** valid to do so, on the other hand, might cause SQLite to return incorrect
+** results.
+*/
+SQLITE_API int sqlite3_vtab_distinct(sqlite3_index_info*);
+
+/*
+** CAPI3REF: Identify and handle IN constraints in xBestIndex
+**
+** This interface may only be used from within an
+** [xBestIndex|xBestIndex() method] of a [virtual table] implementation.
+** The result of invoking this interface from any other context is
+** undefined and probably harmful.
+**
+** ^(A constraint on a virtual table of the form
+** "[IN operator|column IN (...)]" is
+** communicated to the xBestIndex method as a
+** [SQLITE_INDEX_CONSTRAINT_EQ] constraint.)^ If xBestIndex wants to use
+** this constraint, it must set the corresponding
+** aConstraintUsage[].argvIndex to a positive integer. ^(Then, under
+** the usual mode of handling IN operators, SQLite generates [bytecode]
+** that invokes the [xFilter|xFilter() method] once for each value
+** on the right-hand side of the IN operator.)^ Thus the virtual table
+** only sees a single value from the right-hand side of the IN operator
+** at a time.
+**
+** In some cases, however, it would be advantageous for the virtual
+** table to see all values on the right-hand of the IN operator all at
+** once. The sqlite3_vtab_in() interfaces facilitates this in two ways:
+**
+** <ol>
+** <li><p>
+** ^A call to sqlite3_vtab_in(P,N,-1) will return true (non-zero)
+** if and only if the [sqlite3_index_info|P->aConstraint][N] constraint
+** is an [IN operator] that can be processed all at once. ^In other words,
+** sqlite3_vtab_in() with -1 in the third argument is a mechanism
+** by which the virtual table can ask SQLite if all-at-once processing
+** of the IN operator is even possible.
+**
+** <li><p>
+** ^A call to sqlite3_vtab_in(P,N,F) with F==1 or F==0 indicates
+** to SQLite that the virtual table does or does not want to process
+** the IN operator all-at-once, respectively. ^Thus when the third
+** parameter (F) is non-negative, this interface is the mechanism by
+** which the virtual table tells SQLite how it wants to process the
+** IN operator.
+** </ol>
+**
+** ^The sqlite3_vtab_in(P,N,F) interface can be invoked multiple times
+** within the same xBestIndex method call. ^For any given P,N pair,
+** the return value from sqlite3_vtab_in(P,N,F) will always be the same
+** within the same xBestIndex call. ^If the interface returns true
+** (non-zero), that means that the constraint is an IN operator
+** that can be processed all-at-once. ^If the constraint is not an IN
+** operator or cannot be processed all-at-once, then the interface returns
+** false.
+**
+** ^(All-at-once processing of the IN operator is selected if both of the
+** following conditions are met:
+**
+** <ol>
+** <li><p> The P->aConstraintUsage[N].argvIndex value is set to a positive
+** integer. This is how the virtual table tells SQLite that it wants to
+** use the N-th constraint.
+**
+** <li><p> The last call to sqlite3_vtab_in(P,N,F) for which F was
+** non-negative had F>=1.
+** </ol>)^
+**
+** ^If either or both of the conditions above are false, then SQLite uses
+** the traditional one-at-a-time processing strategy for the IN constraint.
+** ^If both conditions are true, then the argvIndex-th parameter to the
+** xFilter method will be an [sqlite3_value] that appears to be NULL,
+** but which can be passed to [sqlite3_vtab_in_first()] and
+** [sqlite3_vtab_in_next()] to find all values on the right-hand side
+** of the IN constraint.
+*/
+SQLITE_API int sqlite3_vtab_in(sqlite3_index_info*, int iCons, int bHandle);
+
+/*
+** CAPI3REF: Find all elements on the right-hand side of an IN constraint.
+**
+** These interfaces are only useful from within the
+** [xFilter|xFilter() method] of a [virtual table] implementation.
+** The result of invoking these interfaces from any other context
+** is undefined and probably harmful.
+**
+** The X parameter in a call to sqlite3_vtab_in_first(X,P) or
+** sqlite3_vtab_in_next(X,P) should be one of the parameters to the
+** xFilter method which invokes these routines, and specifically
+** a parameter that was previously selected for all-at-once IN constraint
+** processing use the [sqlite3_vtab_in()] interface in the
+** [xBestIndex|xBestIndex method]. ^(If the X parameter is not
+** an xFilter argument that was selected for all-at-once IN constraint
+** processing, then these routines return [SQLITE_ERROR].)^
+**
+** ^(Use these routines to access all values on the right-hand side
+** of the IN constraint using code like the following:
+**
+** <blockquote><pre>
+** &nbsp; for(rc=sqlite3_vtab_in_first(pList, &pVal);
+** &nbsp; rc==SQLITE_OK && pVal;
+** &nbsp; rc=sqlite3_vtab_in_next(pList, &pVal)
+** &nbsp; ){
+** &nbsp; // do something with pVal
+** &nbsp; }
+** &nbsp; if( rc!=SQLITE_OK ){
+** &nbsp; // an error has occurred
+** &nbsp; }
+** </pre></blockquote>)^
+**
+** ^On success, the sqlite3_vtab_in_first(X,P) and sqlite3_vtab_in_next(X,P)
+** routines return SQLITE_OK and set *P to point to the first or next value
+** on the RHS of the IN constraint. ^If there are no more values on the
+** right hand side of the IN constraint, then *P is set to NULL and these
+** routines return [SQLITE_DONE]. ^The return value might be
+** some other value, such as SQLITE_NOMEM, in the event of a malfunction.
+**
+** The *ppOut values returned by these routines are only valid until the
+** next call to either of these routines or until the end of the xFilter
+** method from which these routines were called. If the virtual table
+** implementation needs to retain the *ppOut values for longer, it must make
+** copies. The *ppOut values are [protected sqlite3_value|protected].
+*/
+SQLITE_API int sqlite3_vtab_in_first(sqlite3_value *pVal, sqlite3_value **ppOut);
+SQLITE_API int sqlite3_vtab_in_next(sqlite3_value *pVal, sqlite3_value **ppOut);
+
+/*
+** CAPI3REF: Constraint values in xBestIndex()
+** METHOD: sqlite3_index_info
+**
+** This API may only be used from within the [xBestIndex|xBestIndex method]
+** of a [virtual table] implementation. The result of calling this interface
+** from outside of an xBestIndex method are undefined and probably harmful.
+**
+** ^When the sqlite3_vtab_rhs_value(P,J,V) interface is invoked from within
+** the [xBestIndex] method of a [virtual table] implementation, with P being
+** a copy of the [sqlite3_index_info] object pointer passed into xBestIndex and
+** J being a 0-based index into P->aConstraint[], then this routine
+** attempts to set *V to the value of the right-hand operand of
+** that constraint if the right-hand operand is known. ^If the
+** right-hand operand is not known, then *V is set to a NULL pointer.
+** ^The sqlite3_vtab_rhs_value(P,J,V) interface returns SQLITE_OK if
+** and only if *V is set to a value. ^The sqlite3_vtab_rhs_value(P,J,V)
+** inteface returns SQLITE_NOTFOUND if the right-hand side of the J-th
+** constraint is not available. ^The sqlite3_vtab_rhs_value() interface
+** can return an result code other than SQLITE_OK or SQLITE_NOTFOUND if
+** something goes wrong.
+**
+** The sqlite3_vtab_rhs_value() interface is usually only successful if
+** the right-hand operand of a constraint is a literal value in the original
+** SQL statement. If the right-hand operand is an expression or a reference
+** to some other column or a [host parameter], then sqlite3_vtab_rhs_value()
+** will probably return [SQLITE_NOTFOUND].
+**
+** ^(Some constraints, such as [SQLITE_INDEX_CONSTRAINT_ISNULL] and
+** [SQLITE_INDEX_CONSTRAINT_ISNOTNULL], have no right-hand operand. For such
+** constraints, sqlite3_vtab_rhs_value() always returns SQLITE_NOTFOUND.)^
+**
+** ^The [sqlite3_value] object returned in *V is a protected sqlite3_value
+** and remains valid for the duration of the xBestIndex method call.
+** ^When xBestIndex returns, the sqlite3_value object returned by
+** sqlite3_vtab_rhs_value() is automatically deallocated.
+**
+** The "_rhs_" in the name of this routine is an abbreviation for
+** "Right-Hand Side".
+*/
+SQLITE_API int sqlite3_vtab_rhs_value(sqlite3_index_info*, int, sqlite3_value **ppVal);
/*
** CAPI3REF: Conflict resolution modes
@@ -9312,6 +10235,10 @@ SQLITE_API SQLITE_EXPERIMENTAL const char *sqlite3_vtab_collation(sqlite3_index_
** managed by the prepared statement S and will be automatically freed when
** S is finalized.
**
+** Not all values are available for all query elements. When a value is
+** not available, the output variable is set to -1 if the value is numeric,
+** or to NULL if it is a string (SQLITE_SCANSTAT_NAME).
+**
** <dl>
** [[SQLITE_SCANSTAT_NLOOP]] <dt>SQLITE_SCANSTAT_NLOOP</dt>
** <dd>^The [sqlite3_int64] variable pointed to by the V parameter will be
@@ -9339,12 +10266,24 @@ SQLITE_API SQLITE_EXPERIMENTAL const char *sqlite3_vtab_collation(sqlite3_index_
** to a zero-terminated UTF-8 string containing the [EXPLAIN QUERY PLAN]
** description for the X-th loop.
**
-** [[SQLITE_SCANSTAT_SELECTID]] <dt>SQLITE_SCANSTAT_SELECT</dt>
+** [[SQLITE_SCANSTAT_SELECTID]] <dt>SQLITE_SCANSTAT_SELECTID</dt>
** <dd>^The "int" variable pointed to by the V parameter will be set to the
-** "select-id" for the X-th loop. The select-id identifies which query or
-** subquery the loop is part of. The main query has a select-id of zero.
-** The select-id is the same value as is output in the first column
-** of an [EXPLAIN QUERY PLAN] query.
+** id for the X-th query plan element. The id value is unique within the
+** statement. The select-id is the same value as is output in the first
+** column of an [EXPLAIN QUERY PLAN] query.
+**
+** [[SQLITE_SCANSTAT_PARENTID]] <dt>SQLITE_SCANSTAT_PARENTID</dt>
+** <dd>The "int" variable pointed to by the V parameter will be set to the
+** the id of the parent of the current query element, if applicable, or
+** to zero if the query element has no parent. This is the same value as
+** returned in the second column of an [EXPLAIN QUERY PLAN] query.
+**
+** [[SQLITE_SCANSTAT_NCYCLE]] <dt>SQLITE_SCANSTAT_NCYCLE</dt>
+** <dd>The sqlite3_int64 output value is set to the number of cycles,
+** according to the processor time-stamp counter, that elapsed while the
+** query element was being processed. This value is not available for
+** all query elements - if it is unavailable the output variable is
+** set to -1.
** </dl>
*/
#define SQLITE_SCANSTAT_NLOOP 0
@@ -9353,12 +10292,14 @@ SQLITE_API SQLITE_EXPERIMENTAL const char *sqlite3_vtab_collation(sqlite3_index_
#define SQLITE_SCANSTAT_NAME 3
#define SQLITE_SCANSTAT_EXPLAIN 4
#define SQLITE_SCANSTAT_SELECTID 5
+#define SQLITE_SCANSTAT_PARENTID 6
+#define SQLITE_SCANSTAT_NCYCLE 7
/*
** CAPI3REF: Prepared Statement Scan Status
** METHOD: sqlite3_stmt
**
-** This interface returns information about the predicted and measured
+** These interfaces return information about the predicted and measured
** performance for pStmt. Advanced applications can use this
** interface to compare the predicted and the measured performance and
** issue warnings and/or rerun [ANALYZE] if discrepancies are found.
@@ -9369,19 +10310,25 @@ SQLITE_API SQLITE_EXPERIMENTAL const char *sqlite3_vtab_collation(sqlite3_index_
**
** The "iScanStatusOp" parameter determines which status information to return.
** The "iScanStatusOp" must be one of the [scanstatus options] or the behavior
-** of this interface is undefined.
-** ^The requested measurement is written into a variable pointed to by
-** the "pOut" parameter.
-** Parameter "idx" identifies the specific loop to retrieve statistics for.
-** Loops are numbered starting from zero. ^If idx is out of range - less than
-** zero or greater than or equal to the total number of loops used to implement
-** the statement - a non-zero value is returned and the variable that pOut
-** points to is unchanged.
-**
-** ^Statistics might not be available for all loops in all statements. ^In cases
-** where there exist loops with no available statistics, this function behaves
-** as if the loop did not exist - it returns non-zero and leave the variable
-** that pOut points to unchanged.
+** of this interface is undefined. ^The requested measurement is written into
+** a variable pointed to by the "pOut" parameter.
+**
+** The "flags" parameter must be passed a mask of flags. At present only
+** one flag is defined - SQLITE_SCANSTAT_COMPLEX. If SQLITE_SCANSTAT_COMPLEX
+** is specified, then status information is available for all elements
+** of a query plan that are reported by "EXPLAIN QUERY PLAN" output. If
+** SQLITE_SCANSTAT_COMPLEX is not specified, then only query plan elements
+** that correspond to query loops (the "SCAN..." and "SEARCH..." elements of
+** the EXPLAIN QUERY PLAN output) are available. Invoking API
+** sqlite3_stmt_scanstatus() is equivalent to calling
+** sqlite3_stmt_scanstatus_v2() with a zeroed flags parameter.
+**
+** Parameter "idx" identifies the specific query element to retrieve statistics
+** for. Query elements are numbered starting from zero. A value of -1 may be
+** to query for statistics regarding the entire query. ^If idx is out of range
+** - less than -1 or greater than or equal to the total number of query
+** elements used to implement the statement - a non-zero value is returned and
+** the variable that pOut points to is unchanged.
**
** See also: [sqlite3_stmt_scanstatus_reset()]
*/
@@ -9391,6 +10338,19 @@ SQLITE_API int sqlite3_stmt_scanstatus(
int iScanStatusOp, /* Information desired. SQLITE_SCANSTAT_* */
void *pOut /* Result written here */
);
+SQLITE_API int sqlite3_stmt_scanstatus_v2(
+ sqlite3_stmt *pStmt, /* Prepared statement for which info desired */
+ int idx, /* Index of loop to report on */
+ int iScanStatusOp, /* Information desired. SQLITE_SCANSTAT_* */
+ int flags, /* Mask of flags defined below */
+ void *pOut /* Result written here */
+);
+
+/*
+** CAPI3REF: Prepared Statement Scan Status
+** KEYWORDS: {scan status flags}
+*/
+#define SQLITE_SCANSTAT_COMPLEX 0x0001
/*
** CAPI3REF: Zero Scan-Status Counters
@@ -9481,6 +10441,10 @@ SQLITE_API int sqlite3_db_cacheflush(sqlite3*);
** function is not defined for operations on WITHOUT ROWID tables, or for
** DELETE operations on rowid tables.
**
+** ^The sqlite3_preupdate_hook(D,C,P) function returns the P argument from
+** the previous call on the same [database connection] D, or NULL for
+** the first call on D.
+**
** The [sqlite3_preupdate_old()], [sqlite3_preupdate_new()],
** [sqlite3_preupdate_count()], and [sqlite3_preupdate_depth()] interfaces
** provide additional information about a preupdate event. These routines
@@ -9517,6 +10481,15 @@ SQLITE_API int sqlite3_db_cacheflush(sqlite3*);
** triggers; or 2 for changes resulting from triggers called by top-level
** triggers; and so forth.
**
+** When the [sqlite3_blob_write()] API is used to update a blob column,
+** the pre-update hook is invoked with SQLITE_DELETE. This is because the
+** in this case the new values are not available. In this case, when a
+** callback made with op==SQLITE_DELETE is actually a write using the
+** sqlite3_blob_write() API, the [sqlite3_preupdate_blobwrite()] returns
+** the index of the column being written. In other cases, where the
+** pre-update hook is being invoked for some other reason, including a
+** regular DELETE, sqlite3_preupdate_blobwrite() returns -1.
+**
** See also: [sqlite3_update_hook()]
*/
#if defined(SQLITE_ENABLE_PREUPDATE_HOOK)
@@ -9537,6 +10510,7 @@ SQLITE_API int sqlite3_preupdate_old(sqlite3 *, int, sqlite3_value **);
SQLITE_API int sqlite3_preupdate_count(sqlite3 *);
SQLITE_API int sqlite3_preupdate_depth(sqlite3 *);
SQLITE_API int sqlite3_preupdate_new(sqlite3 *, int, sqlite3_value **);
+SQLITE_API int sqlite3_preupdate_blobwrite(sqlite3 *);
#endif
/*
@@ -9588,6 +10562,14 @@ typedef struct sqlite3_snapshot {
** If there is not already a read-transaction open on schema S when
** this function is called, one is opened automatically.
**
+** If a read-transaction is opened by this function, then it is guaranteed
+** that the returned snapshot object may not be invalidated by a database
+** writer or checkpointer until after the read-transaction is closed. This
+** is not guaranteed if a read-transaction is already open when this
+** function is called. In that case, any subsequent write or checkpoint
+** operation on the database may invalidate the returned snapshot handle,
+** even while the read-transaction remains open.
+**
** The following must be true for this function to succeed. If any of
** the following statements are false when sqlite3_snapshot_get() is
** called, SQLITE_ERROR is returned. The final value of *P is undefined
@@ -9771,12 +10753,19 @@ SQLITE_API SQLITE_EXPERIMENTAL int sqlite3_snapshot_recover(sqlite3 *db, const c
** SQLITE_SERIALIZE_NOCOPY bit is set but no contiguous copy
** of the database exists.
**
+** After the call, if the SQLITE_SERIALIZE_NOCOPY bit had been set,
+** the returned buffer content will remain accessible and unchanged
+** until either the next write operation on the connection or when
+** the connection is closed, and applications must not modify the
+** buffer. If the bit had been clear, the returned buffer will not
+** be accessed by SQLite after the call.
+**
** A call to sqlite3_serialize(D,S,P,F) might return NULL even if the
** SQLITE_SERIALIZE_NOCOPY bit is omitted from argument F if a memory
** allocation error occurs.
**
-** This interface is only available if SQLite is compiled with the
-** [SQLITE_ENABLE_DESERIALIZE] option.
+** This interface is omitted if SQLite is compiled with the
+** [SQLITE_OMIT_DESERIALIZE] option.
*/
SQLITE_API unsigned char *sqlite3_serialize(
sqlite3 *db, /* The database connection */
@@ -9819,16 +10808,30 @@ SQLITE_API unsigned char *sqlite3_serialize(
** SQLite will try to increase the buffer size using sqlite3_realloc64()
** if writes on the database cause it to grow larger than M bytes.
**
+** Applications must not modify the buffer P or invalidate it before
+** the database connection D is closed.
+**
** The sqlite3_deserialize() interface will fail with SQLITE_BUSY if the
** database is currently in a read transaction or is involved in a backup
** operation.
**
+** It is not possible to deserialized into the TEMP database. If the
+** S argument to sqlite3_deserialize(D,S,P,N,M,F) is "temp" then the
+** function returns SQLITE_ERROR.
+**
+** The deserialized database should not be in [WAL mode]. If the database
+** is in WAL mode, then any attempt to use the database file will result
+** in an [SQLITE_CANTOPEN] error. The application can set the
+** [file format version numbers] (bytes 18 and 19) of the input database P
+** to 0x01 prior to invoking sqlite3_deserialize(D,S,P,N,M,F) to force the
+** database file into rollback mode and work around this limitation.
+**
** If sqlite3_deserialize(D,S,P,N,M,F) fails for any reason and if the
** SQLITE_DESERIALIZE_FREEONCLOSE bit is set in argument F, then
** [sqlite3_free()] is invoked on argument P prior to returning.
**
-** This interface is only available if SQLite is compiled with the
-** [SQLITE_ENABLE_DESERIALIZE] option.
+** This interface is omitted if SQLite is compiled with the
+** [SQLITE_OMIT_DESERIALIZE] option.
*/
SQLITE_API int sqlite3_deserialize(
sqlite3 *db, /* The database connection */
@@ -9872,6 +10875,17 @@ SQLITE_API int sqlite3_deserialize(
# undef double
#endif
+#if defined(__wasi__)
+# undef SQLITE_WASI
+# define SQLITE_WASI 1
+# ifndef SQLITE_OMIT_LOAD_EXTENSION
+# define SQLITE_OMIT_LOAD_EXTENSION
+# endif
+# ifndef SQLITE_THREADSAFE
+# define SQLITE_THREADSAFE 0
+# endif
+#endif
+
#ifdef __cplusplus
} /* End of the 'extern "C"' block */
#endif
@@ -10077,6 +11091,51 @@ SQLITE_API int sqlite3session_create(
*/
SQLITE_API void sqlite3session_delete(sqlite3_session *pSession);
+/*
+** CAPI3REF: Configure a Session Object
+** METHOD: sqlite3_session
+**
+** This method is used to configure a session object after it has been
+** created. At present the only valid values for the second parameter are
+** [SQLITE_SESSION_OBJCONFIG_SIZE] and [SQLITE_SESSION_OBJCONFIG_ROWID].
+**
+*/
+SQLITE_API int sqlite3session_object_config(sqlite3_session*, int op, void *pArg);
+
+/*
+** CAPI3REF: Options for sqlite3session_object_config
+**
+** The following values may passed as the the 2nd parameter to
+** sqlite3session_object_config().
+**
+** <dt>SQLITE_SESSION_OBJCONFIG_SIZE <dd>
+** This option is used to set, clear or query the flag that enables
+** the [sqlite3session_changeset_size()] API. Because it imposes some
+** computational overhead, this API is disabled by default. Argument
+** pArg must point to a value of type (int). If the value is initially
+** 0, then the sqlite3session_changeset_size() API is disabled. If it
+** is greater than 0, then the same API is enabled. Or, if the initial
+** value is less than zero, no change is made. In all cases the (int)
+** variable is set to 1 if the sqlite3session_changeset_size() API is
+** enabled following the current call, or 0 otherwise.
+**
+** It is an error (SQLITE_MISUSE) to attempt to modify this setting after
+** the first table has been attached to the session object.
+**
+** <dt>SQLITE_SESSION_OBJCONFIG_ROWID <dd>
+** This option is used to set, clear or query the flag that enables
+** collection of data for tables with no explicit PRIMARY KEY.
+**
+** Normally, tables with no explicit PRIMARY KEY are simply ignored
+** by the sessions module. However, if this flag is set, it behaves
+** as if such tables have a column "_rowid_ INTEGER PRIMARY KEY" inserted
+** as their leftmost columns.
+**
+** It is an error (SQLITE_MISUSE) to attempt to modify this setting after
+** the first table has been attached to the session object.
+*/
+#define SQLITE_SESSION_OBJCONFIG_SIZE 1
+#define SQLITE_SESSION_OBJCONFIG_ROWID 2
/*
** CAPI3REF: Enable Or Disable A Session Object
@@ -10322,6 +11381,22 @@ SQLITE_API int sqlite3session_changeset(
);
/*
+** CAPI3REF: Return An Upper-limit For The Size Of The Changeset
+** METHOD: sqlite3_session
+**
+** By default, this function always returns 0. For it to return
+** a useful result, the sqlite3_session object must have been configured
+** to enable this API using sqlite3session_object_config() with the
+** SQLITE_SESSION_OBJCONFIG_SIZE verb.
+**
+** When enabled, this function returns an upper limit, in bytes, for the size
+** of the changeset that might be produced if sqlite3session_changeset() were
+** called. The final changeset size might be equal to or smaller than the
+** size in bytes returned by this function.
+*/
+SQLITE_API sqlite3_int64 sqlite3session_changeset_size(sqlite3_session *pSession);
+
+/*
** CAPI3REF: Load The Difference Between Tables Into A Session
** METHOD: sqlite3_session
**
@@ -10439,6 +11514,14 @@ SQLITE_API int sqlite3session_patchset(
SQLITE_API int sqlite3session_isempty(sqlite3_session *pSession);
/*
+** CAPI3REF: Query for the amount of heap memory used by a session object.
+**
+** This API returns the total amount of heap memory in bytes currently
+** used by the session object passed as the only argument.
+*/
+SQLITE_API sqlite3_int64 sqlite3session_memory_used(sqlite3_session *pSession);
+
+/*
** CAPI3REF: Create An Iterator To Traverse A Changeset
** CONSTRUCTOR: sqlite3_changeset_iter
**
@@ -10540,18 +11623,23 @@ SQLITE_API int sqlite3changeset_next(sqlite3_changeset_iter *pIter);
** call to [sqlite3changeset_next()] must have returned [SQLITE_ROW]. If this
** is not the case, this function returns [SQLITE_MISUSE].
**
-** If argument pzTab is not NULL, then *pzTab is set to point to a
-** nul-terminated utf-8 encoded string containing the name of the table
-** affected by the current change. The buffer remains valid until either
-** sqlite3changeset_next() is called on the iterator or until the
-** conflict-handler function returns. If pnCol is not NULL, then *pnCol is
-** set to the number of columns in the table affected by the change. If
-** pbIndirect is not NULL, then *pbIndirect is set to true (1) if the change
+** Arguments pOp, pnCol and pzTab may not be NULL. Upon return, three
+** outputs are set through these pointers:
+**
+** *pOp is set to one of [SQLITE_INSERT], [SQLITE_DELETE] or [SQLITE_UPDATE],
+** depending on the type of change that the iterator currently points to;
+**
+** *pnCol is set to the number of columns in the table affected by the change; and
+**
+** *pzTab is set to point to a nul-terminated utf-8 encoded string containing
+** the name of the table affected by the current change. The buffer remains
+** valid until either sqlite3changeset_next() is called on the iterator
+** or until the conflict-handler function returns.
+**
+** If pbIndirect is not NULL, then *pbIndirect is set to true (1) if the change
** is an indirect change, or false (0) otherwise. See the documentation for
** [sqlite3session_indirect()] for a description of direct and indirect
-** changes. Finally, if pOp is not NULL, then *pOp is set to one of
-** [SQLITE_INSERT], [SQLITE_DELETE] or [SQLITE_UPDATE], depending on the
-** type of change that the iterator currently points to.
+** changes.
**
** If no error occurs, SQLITE_OK is returned. If an error does occur, an
** SQLite error code is returned. The values of the output variables may not
@@ -10809,6 +11897,18 @@ SQLITE_API int sqlite3changeset_concat(
/*
+** CAPI3REF: Upgrade the Schema of a Changeset/Patchset
+*/
+SQLITE_API int sqlite3changeset_upgrade(
+ sqlite3 *db,
+ const char *zDb,
+ int nIn, const void *pIn, /* Input changeset */
+ int *pnOut, void **ppOut /* OUT: Inverse of input */
+);
+
+
+
+/*
** CAPI3REF: Changegroup Handle
**
** A changegroup is an object used to combine two or more
@@ -10855,6 +11955,38 @@ typedef struct sqlite3_changegroup sqlite3_changegroup;
SQLITE_API int sqlite3changegroup_new(sqlite3_changegroup **pp);
/*
+** CAPI3REF: Add a Schema to a Changegroup
+** METHOD: sqlite3_changegroup_schema
+**
+** This method may be used to optionally enforce the rule that the changesets
+** added to the changegroup handle must match the schema of database zDb
+** ("main", "temp", or the name of an attached database). If
+** sqlite3changegroup_add() is called to add a changeset that is not compatible
+** with the configured schema, SQLITE_SCHEMA is returned and the changegroup
+** object is left in an undefined state.
+**
+** A changeset schema is considered compatible with the database schema in
+** the same way as for sqlite3changeset_apply(). Specifically, for each
+** table in the changeset, there exists a database table with:
+**
+** <ul>
+** <li> The name identified by the changeset, and
+** <li> at least as many columns as recorded in the changeset, and
+** <li> the primary key columns in the same position as recorded in
+** the changeset.
+** </ul>
+**
+** The output of the changegroup object always has the same schema as the
+** database nominated using this function. In cases where changesets passed
+** to sqlite3changegroup_add() have fewer columns than the corresponding table
+** in the database schema, these are filled in using the default column
+** values from the database schema. This makes it possible to combined
+** changesets that have different numbers of columns for a single table
+** within a changegroup, provided that they are otherwise compatible.
+*/
+SQLITE_API int sqlite3changegroup_schema(sqlite3_changegroup*, sqlite3*, const char *zDb);
+
+/*
** CAPI3REF: Add A Changeset To A Changegroup
** METHOD: sqlite3_changegroup
**
@@ -10922,17 +12054,46 @@ SQLITE_API int sqlite3changegroup_new(sqlite3_changegroup **pp);
** If the new changeset contains changes to a table that is already present
** in the changegroup, then the number of columns and the position of the
** primary key columns for the table must be consistent. If this is not the
-** case, this function fails with SQLITE_SCHEMA. If the input changeset
-** appears to be corrupt and the corruption is detected, SQLITE_CORRUPT is
-** returned. Or, if an out-of-memory condition occurs during processing, this
-** function returns SQLITE_NOMEM. In all cases, if an error occurs the state
-** of the final contents of the changegroup is undefined.
+** case, this function fails with SQLITE_SCHEMA. Except, if the changegroup
+** object has been configured with a database schema using the
+** sqlite3changegroup_schema() API, then it is possible to combine changesets
+** with different numbers of columns for a single table, provided that
+** they are otherwise compatible.
+**
+** If the input changeset appears to be corrupt and the corruption is
+** detected, SQLITE_CORRUPT is returned. Or, if an out-of-memory condition
+** occurs during processing, this function returns SQLITE_NOMEM.
**
-** If no error occurs, SQLITE_OK is returned.
+** In all cases, if an error occurs the state of the final contents of the
+** changegroup is undefined. If no error occurs, SQLITE_OK is returned.
*/
SQLITE_API int sqlite3changegroup_add(sqlite3_changegroup*, int nData, void *pData);
/*
+** CAPI3REF: Add A Single Change To A Changegroup
+** METHOD: sqlite3_changegroup
+**
+** This function adds the single change currently indicated by the iterator
+** passed as the second argument to the changegroup object. The rules for
+** adding the change are just as described for [sqlite3changegroup_add()].
+**
+** If the change is successfully added to the changegroup, SQLITE_OK is
+** returned. Otherwise, an SQLite error code is returned.
+**
+** The iterator must point to a valid entry when this function is called.
+** If it does not, SQLITE_ERROR is returned and no change is added to the
+** changegroup. Additionally, the iterator must not have been opened with
+** the SQLITE_CHANGESETAPPLY_INVERT flag. In this case SQLITE_ERROR is also
+** returned.
+*/
+SQLITE_API int sqlite3changegroup_add_change(
+ sqlite3_changegroup*,
+ sqlite3_changeset_iter*
+);
+
+
+
+/*
** CAPI3REF: Obtain A Composite Changeset From A Changegroup
** METHOD: sqlite3_changegroup
**
@@ -11180,9 +12341,30 @@ SQLITE_API int sqlite3changeset_apply_v2(
** Invert the changeset before applying it. This is equivalent to inverting
** a changeset using sqlite3changeset_invert() before applying it. It is
** an error to specify this flag with a patchset.
+**
+** <dt>SQLITE_CHANGESETAPPLY_IGNORENOOP <dd>
+** Do not invoke the conflict handler callback for any changes that
+** would not actually modify the database even if they were applied.
+** Specifically, this means that the conflict handler is not invoked
+** for:
+** <ul>
+** <li>a delete change if the row being deleted cannot be found,
+** <li>an update change if the modified fields are already set to
+** their new values in the conflicting row, or
+** <li>an insert change if all fields of the conflicting row match
+** the row being inserted.
+** </ul>
+**
+** <dt>SQLITE_CHANGESETAPPLY_FKNOACTION <dd>
+** If this flag it set, then all foreign key constraints in the target
+** database behave as if they were declared with "ON UPDATE NO ACTION ON
+** DELETE NO ACTION", even if they are actually CASCADE, RESTRICT, SET NULL
+** or SET DEFAULT.
*/
#define SQLITE_CHANGESETAPPLY_NOSAVEPOINT 0x0001
#define SQLITE_CHANGESETAPPLY_INVERT 0x0002
+#define SQLITE_CHANGESETAPPLY_IGNORENOOP 0x0004
+#define SQLITE_CHANGESETAPPLY_FKNOACTION 0x0008
/*
** CAPI3REF: Constants Passed To The Conflict Handler
@@ -11715,8 +12897,8 @@ struct Fts5PhraseIter {
** EXTENSION API FUNCTIONS
**
** xUserData(pFts):
-** Return a copy of the context pointer the extension function was
-** registered with.
+** Return a copy of the pUserData pointer passed to the xCreateFunction()
+** API when the extension function was registered.
**
** xColumnTotalSize(pFts, iCol, pnToken):
** If parameter iCol is less than zero, set output variable *pnToken
@@ -11748,8 +12930,11 @@ struct Fts5PhraseIter {
** created with the "columnsize=0" option.
**
** xColumnText:
-** This function attempts to retrieve the text of column iCol of the
-** current document. If successful, (*pz) is set to point to a buffer
+** If parameter iCol is less than zero, or greater than or equal to the
+** number of columns in the table, SQLITE_RANGE is returned.
+**
+** Otherwise, this function attempts to retrieve the text of column iCol of
+** the current document. If successful, (*pz) is set to point to a buffer
** containing the text in utf-8 encoding, (*pn) is set to the size in bytes
** (not characters) of the buffer and SQLITE_OK is returned. Otherwise,
** if an error occurs, an SQLite error code is returned and the final values
@@ -11759,8 +12944,10 @@ struct Fts5PhraseIter {
** Returns the number of phrases in the current query expression.
**
** xPhraseSize:
-** Returns the number of tokens in phrase iPhrase of the query. Phrases
-** are numbered starting from zero.
+** If parameter iCol is less than zero, or greater than or equal to the
+** number of phrases in the current query, as returned by xPhraseCount,
+** 0 is returned. Otherwise, this function returns the number of tokens in
+** phrase iPhrase of the query. Phrases are numbered starting from zero.
**
** xInstCount:
** Set *pnInst to the total number of occurrences of all phrases within
@@ -11776,12 +12963,13 @@ struct Fts5PhraseIter {
** Query for the details of phrase match iIdx within the current row.
** Phrase matches are numbered starting from zero, so the iIdx argument
** should be greater than or equal to zero and smaller than the value
-** output by xInstCount().
+** output by xInstCount(). If iIdx is less than zero or greater than
+** or equal to the value returned by xInstCount(), SQLITE_RANGE is returned.
**
-** Usually, output parameter *piPhrase is set to the phrase number, *piCol
+** Otherwise, output parameter *piPhrase is set to the phrase number, *piCol
** to the column in which it occurs and *piOff the token offset of the
-** first token of the phrase. Returns SQLITE_OK if successful, or an error
-** code (i.e. SQLITE_NOMEM) if an error occurs.
+** first token of the phrase. SQLITE_OK is returned if successful, or an
+** error code (i.e. SQLITE_NOMEM) if an error occurs.
**
** This API can be quite slow if used with an FTS5 table created with the
** "detail=none" or "detail=column" option.
@@ -11807,6 +12995,10 @@ struct Fts5PhraseIter {
** Invoking Api.xUserData() returns a copy of the pointer passed as
** the third argument to pUserData.
**
+** If parameter iPhrase is less than zero, or greater than or equal to
+** the number of phrases in the query, as returned by xPhraseCount(),
+** this function returns SQLITE_RANGE.
+**
** If the callback function returns any value other than SQLITE_OK, the
** query is abandoned and the xQueryPhrase function returns immediately.
** If the returned value is SQLITE_DONE, xQueryPhrase returns SQLITE_OK.
@@ -11888,6 +13080,10 @@ struct Fts5PhraseIter {
** (i.e. if it is a contentless table), then this API always iterates
** through an empty set (all calls to xPhraseFirst() set iCol to -1).
**
+** In all cases, matches are visited in (column ASC, offset ASC) order.
+** i.e. all those in column 0, sorted by offset, followed by those in
+** column 1, etc.
+**
** xPhraseNext()
** See xPhraseFirst above.
**
@@ -11921,9 +13117,65 @@ struct Fts5PhraseIter {
**
** xPhraseNextColumn()
** See xPhraseFirstColumn above.
+**
+** xQueryToken(pFts5, iPhrase, iToken, ppToken, pnToken)
+** This is used to access token iToken of phrase iPhrase of the current
+** query. Before returning, output parameter *ppToken is set to point
+** to a buffer containing the requested token, and *pnToken to the
+** size of this buffer in bytes.
+**
+** If iPhrase or iToken are less than zero, or if iPhrase is greater than
+** or equal to the number of phrases in the query as reported by
+** xPhraseCount(), or if iToken is equal to or greater than the number of
+** tokens in the phrase, SQLITE_RANGE is returned and *ppToken and *pnToken
+ are both zeroed.
+**
+** The output text is not a copy of the query text that specified the
+** token. It is the output of the tokenizer module. For tokendata=1
+** tables, this includes any embedded 0x00 and trailing data.
+**
+** xInstToken(pFts5, iIdx, iToken, ppToken, pnToken)
+** This is used to access token iToken of phrase hit iIdx within the
+** current row. If iIdx is less than zero or greater than or equal to the
+** value returned by xInstCount(), SQLITE_RANGE is returned. Otherwise,
+** output variable (*ppToken) is set to point to a buffer containing the
+** matching document token, and (*pnToken) to the size of that buffer in
+** bytes. This API is not available if the specified token matches a
+** prefix query term. In that case both output variables are always set
+** to 0.
+**
+** The output text is not a copy of the document text that was tokenized.
+** It is the output of the tokenizer module. For tokendata=1 tables, this
+** includes any embedded 0x00 and trailing data.
+**
+** This API can be quite slow if used with an FTS5 table created with the
+** "detail=none" or "detail=column" option.
+**
+** xColumnLocale(pFts5, iIdx, pzLocale, pnLocale)
+** If parameter iCol is less than zero, or greater than or equal to the
+** number of columns in the table, SQLITE_RANGE is returned.
+**
+** Otherwise, this function attempts to retrieve the locale associated
+** with column iCol of the current row. Usually, there is no associated
+** locale, and output parameters (*pzLocale) and (*pnLocale) are set
+** to NULL and 0, respectively. However, if the fts5_locale() function
+** was used to associate a locale with the value when it was inserted
+** into the fts5 table, then (*pzLocale) is set to point to a nul-terminated
+** buffer containing the name of the locale in utf-8 encoding. (*pnLocale)
+** is set to the size in bytes of the buffer, not including the
+** nul-terminator.
+**
+** If successful, SQLITE_OK is returned. Or, if an error occurs, an
+** SQLite error code is returned. The final value of the output parameters
+** is undefined in this case.
+**
+** xTokenize_v2:
+** Tokenize text using the tokenizer belonging to the FTS5 table. This
+** API is the same as the xTokenize() API, except that it allows a tokenizer
+** locale to be specified.
*/
struct Fts5ExtensionApi {
- int iVersion; /* Currently always set to 3 */
+ int iVersion; /* Currently always set to 4 */
void *(*xUserData)(Fts5Context*);
@@ -11958,6 +13210,22 @@ struct Fts5ExtensionApi {
int (*xPhraseFirstColumn)(Fts5Context*, int iPhrase, Fts5PhraseIter*, int*);
void (*xPhraseNextColumn)(Fts5Context*, Fts5PhraseIter*, int *piCol);
+
+ /* Below this point are iVersion>=3 only */
+ int (*xQueryToken)(Fts5Context*,
+ int iPhrase, int iToken,
+ const char **ppToken, int *pnToken
+ );
+ int (*xInstToken)(Fts5Context*, int iIdx, int iToken, const char**, int*);
+
+ /* Below this point are iVersion>=4 only */
+ int (*xColumnLocale)(Fts5Context*, int iCol, const char **pz, int *pn);
+ int (*xTokenize_v2)(Fts5Context*,
+ const char *pText, int nText, /* Text to tokenize */
+ const char *pLocale, int nLocale, /* Locale to pass to tokenizer */
+ void *pCtx, /* Context passed to xToken() */
+ int (*xToken)(void*, int, const char*, int, int, int) /* Callback */
+ );
};
/*
@@ -11978,7 +13246,7 @@ struct Fts5ExtensionApi {
** A tokenizer instance is required to actually tokenize text.
**
** The first argument passed to this function is a copy of the (void*)
-** pointer provided by the application when the fts5_tokenizer object
+** pointer provided by the application when the fts5_tokenizer_v2 object
** was registered with FTS5 (the third argument to xCreateTokenizer()).
** The second and third arguments are an array of nul-terminated strings
** containing the tokenizer arguments, if any, specified following the
@@ -12002,7 +13270,7 @@ struct Fts5ExtensionApi {
** argument passed to this function is a pointer to an Fts5Tokenizer object
** returned by an earlier call to xCreate().
**
-** The second argument indicates the reason that FTS5 is requesting
+** The third argument indicates the reason that FTS5 is requesting
** tokenization of the supplied text. This is always one of the following
** four values:
**
@@ -12026,6 +13294,13 @@ struct Fts5ExtensionApi {
** on a columnsize=0 database.
** </ul>
**
+** The sixth and seventh arguments passed to xTokenize() - pLocale and
+** nLocale - are a pointer to a buffer containing the locale to use for
+** tokenization (e.g. "en_US") and its size in bytes, respectively. The
+** pLocale buffer is not nul-terminated. pLocale may be passed NULL (in
+** which case nLocale is always 0) to indicate that the tokenizer should
+** use its default locale.
+**
** For each token in the input string, the supplied callback xToken() must
** be invoked. The first argument to it should be a copy of the pointer
** passed as the second argument to xTokenize(). The third and fourth
@@ -12049,6 +13324,30 @@ struct Fts5ExtensionApi {
** may abandon the tokenization and return any error code other than
** SQLITE_OK or SQLITE_DONE.
**
+** If the tokenizer is registered using an fts5_tokenizer_v2 object,
+** then the xTokenize() method has two additional arguments - pLocale
+** and nLocale. These specify the locale that the tokenizer should use
+** for the current request. If pLocale and nLocale are both 0, then the
+** tokenizer should use its default locale. Otherwise, pLocale points to
+** an nLocale byte buffer containing the name of the locale to use as utf-8
+** text. pLocale is not nul-terminated.
+**
+** FTS5_TOKENIZER
+**
+** There is also an fts5_tokenizer object. This is an older, deprecated,
+** version of fts5_tokenizer_v2. It is similar except that:
+**
+** <ul>
+** <li> There is no "iVersion" field, and
+** <li> The xTokenize() method does not take a locale argument.
+** </ul>
+**
+** Legacy fts5_tokenizer tokenizers must be registered using the
+** legacy xCreateTokenizer() function, instead of xCreateTokenizer_v2().
+**
+** Tokenizer implementations registered using either API may be retrieved
+** using both xFindTokenizer() and xFindTokenizer_v2().
+**
** SYNONYM SUPPORT
**
** Custom tokenizers may also support synonyms. Consider a case in which a
@@ -12152,11 +13451,38 @@ struct Fts5ExtensionApi {
** as separate queries of the FTS index are required for each synonym.
**
** When using methods (2) or (3), it is important that the tokenizer only
-** provide synonyms when tokenizing document text (method (2)) or query
-** text (method (3)), not both. Doing so will not cause any errors, but is
+** provide synonyms when tokenizing document text (method (3)) or query
+** text (method (2)), not both. Doing so will not cause any errors, but is
** inefficient.
*/
typedef struct Fts5Tokenizer Fts5Tokenizer;
+typedef struct fts5_tokenizer_v2 fts5_tokenizer_v2;
+struct fts5_tokenizer_v2 {
+ int iVersion; /* Currently always 2 */
+
+ int (*xCreate)(void*, const char **azArg, int nArg, Fts5Tokenizer **ppOut);
+ void (*xDelete)(Fts5Tokenizer*);
+ int (*xTokenize)(Fts5Tokenizer*,
+ void *pCtx,
+ int flags, /* Mask of FTS5_TOKENIZE_* flags */
+ const char *pText, int nText,
+ const char *pLocale, int nLocale,
+ int (*xToken)(
+ void *pCtx, /* Copy of 2nd argument to xTokenize() */
+ int tflags, /* Mask of FTS5_TOKEN_* flags */
+ const char *pToken, /* Pointer to buffer containing token */
+ int nToken, /* Size of token in bytes */
+ int iStart, /* Byte offset of token within input text */
+ int iEnd /* Byte offset of end of token within input text */
+ )
+ );
+};
+
+/*
+** New code should use the fts5_tokenizer_v2 type to define tokenizer
+** implementations. The following type is included for legacy applications
+** that still use it.
+*/
typedef struct fts5_tokenizer fts5_tokenizer;
struct fts5_tokenizer {
int (*xCreate)(void*, const char **azArg, int nArg, Fts5Tokenizer **ppOut);
@@ -12176,6 +13502,7 @@ struct fts5_tokenizer {
);
};
+
/* Flags that may be passed as the third argument to xTokenize() */
#define FTS5_TOKENIZE_QUERY 0x0001
#define FTS5_TOKENIZE_PREFIX 0x0002
@@ -12195,13 +13522,13 @@ struct fts5_tokenizer {
*/
typedef struct fts5_api fts5_api;
struct fts5_api {
- int iVersion; /* Currently always set to 2 */
+ int iVersion; /* Currently always set to 3 */
/* Create a new tokenizer */
int (*xCreateTokenizer)(
fts5_api *pApi,
const char *zName,
- void *pContext,
+ void *pUserData,
fts5_tokenizer *pTokenizer,
void (*xDestroy)(void*)
);
@@ -12210,7 +13537,7 @@ struct fts5_api {
int (*xFindTokenizer)(
fts5_api *pApi,
const char *zName,
- void **ppContext,
+ void **ppUserData,
fts5_tokenizer *pTokenizer
);
@@ -12218,10 +13545,29 @@ struct fts5_api {
int (*xCreateFunction)(
fts5_api *pApi,
const char *zName,
- void *pContext,
+ void *pUserData,
fts5_extension_function xFunction,
void (*xDestroy)(void*)
);
+
+ /* APIs below this point are only available if iVersion>=3 */
+
+ /* Create a new tokenizer */
+ int (*xCreateTokenizer_v2)(
+ fts5_api *pApi,
+ const char *zName,
+ void *pUserData,
+ fts5_tokenizer_v2 *pTokenizer,
+ void (*xDestroy)(void*)
+ );
+
+ /* Find an existing tokenizer */
+ int (*xFindTokenizer_v2)(
+ fts5_api *pApi,
+ const char *zName,
+ void **ppUserData,
+ fts5_tokenizer_v2 **ppTokenizer
+ );
};
/*
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/sqlquery.h b/SQLiteStudio3/coreSQLiteStudio/db/sqlquery.h
index 1eea25c..f786590 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/sqlquery.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/sqlquery.h
@@ -302,7 +302,7 @@ class API_EXPORT SqlQuery
*/
QList<SqlResultsRowPtr> preloadedData;
- int affected = 0;
+ qint64 affected = 0;
QString query;
QVariant queryArgs;
diff --git a/SQLiteStudio3/coreSQLiteStudio/db/stdsqlite3driver.h b/SQLiteStudio3/coreSQLiteStudio/db/stdsqlite3driver.h
index c8a3ba3..74db720 100644
--- a/SQLiteStudio3/coreSQLiteStudio/db/stdsqlite3driver.h
+++ b/SQLiteStudio3/coreSQLiteStudio/db/stdsqlite3driver.h
@@ -20,6 +20,7 @@
static const int BUSY = UppercasePrefix##SQLITE_BUSY; \
static const int ROW = UppercasePrefix##SQLITE_ROW; \
static const int DONE = UppercasePrefix##SQLITE_DONE; \
+ static const int INTERRUPT = UppercasePrefix##SQLITE_INTERRUPT; \
static const int CHECKPOINT_PASSIVE = UppercasePrefix##SQLITE_CHECKPOINT_PASSIVE; \
static const int CHECKPOINT_FULL = UppercasePrefix##SQLITE_CHECKPOINT_FULL; \
static const int CHECKPOINT_RESTART = UppercasePrefix##SQLITE_CHECKPOINT_RESTART; \
@@ -34,6 +35,7 @@
\
static destructor_type TRANSIENT() {return UppercasePrefix##SQLITE_TRANSIENT;} \
static void interrupt(handle* arg) {Prefix##sqlite3_interrupt(arg);} \
+ static int is_interrupted(handle* arg) {return Prefix##sqlite3_is_interrupted(arg);} \
static const void *value_blob(value* arg) {return Prefix##sqlite3_value_blob(arg);} \
static double value_double(value* arg) {return Prefix##sqlite3_value_double(arg);} \
static int64 value_int64(value* arg) {return Prefix##sqlite3_value_int64(arg);} \
@@ -74,11 +76,14 @@
static const char *column_origin_name(stmt* arg1, int arg2) {return Prefix##sqlite3_column_origin_name(arg1, arg2);} \
static int changes(handle* arg) {return Prefix##sqlite3_changes(arg);} \
static int total_changes(handle* arg) {return Prefix##sqlite3_total_changes(arg);} \
+ static int64 total_changes64(handle* arg) {return Prefix##sqlite3_total_changes(arg);} \
static int64 last_insert_rowid(handle* arg) {return Prefix##sqlite3_last_insert_rowid(arg);} \
static int step(stmt* arg) {return Prefix##sqlite3_step(arg);} \
static int reset(stmt* arg) {return Prefix##sqlite3_reset(arg);} \
static int close(handle* arg) {return Prefix##sqlite3_close(arg);} \
static void free(void* arg) {return Prefix##sqlite3_free(arg);} \
+ static int threadsafe() {return Prefix##sqlite3_threadsafe();} \
+ static int get_autocommit(handle* arg) {return Prefix##sqlite3_get_autocommit(arg);} \
static int wal_checkpoint(handle* arg1, const char* arg2) {return Prefix##sqlite3_wal_checkpoint(arg1, arg2);} \
static int wal_checkpoint_v2(handle* a1, const char* a2, int a3, int* a4, int* a5) {return Prefix##sqlite3_wal_checkpoint_v2(a1, a2, a3, a4, a5);} \
static int enable_load_extension(handle* arg1, int arg2) {return Prefix##sqlite3_enable_load_extension(arg1, arg2);} \
diff --git a/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.cpp b/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.cpp
index 1c206f9..eb01b86 100644
--- a/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.cpp
@@ -137,7 +137,6 @@ void DbObjectOrganizer::copyOrMoveObjectsToDb(Db* srcDb, const QSet<QString>& ob
void DbObjectOrganizer::processPreparation()
{
- StrHash<SqliteQueryPtr> allParsedObjects = srcResolver->getAllParsedObjects();
StrHash<SchemaResolver::ObjectDetails> details = srcResolver->getAllObjectDetails();
for (const QString& srcName : srcNames)
{
@@ -151,7 +150,7 @@ void DbObjectOrganizer::processPreparation()
{
case SchemaResolver::TABLE:
srcTables << srcName;
- collectReferencedTables(srcName, allParsedObjects);
+ collectReferencedTables(srcName);
collectReferencedIndexes(srcName);
collectReferencedTriggersForTable(srcName);
break;
@@ -488,7 +487,7 @@ bool DbObjectOrganizer::copyDataUsingAttach(const QString& table)
QString wrappedSrcTable = wrapObjIfNeeded(srcTable);
QString wrappedDstTable = wrapObjIfNeeded(table);
QStringList srcColumns = srcResolver->getTableColumns(srcTable, true);
- QString srcColumnsStr = srcColumns.join(", ");
+ QString srcColumnsStr = wrapObjNamesIfNeeded(srcColumns).join(", ");
SqlQueryPtr results = srcDb->exec(insertTpl.arg(attachName, wrappedDstTable, srcColumnsStr, wrappedSrcTable));
if (results->isError())
{
@@ -544,7 +543,12 @@ bool DbObjectOrganizer::copySimpleObjectToDb(const QString& name, const QString&
if (ddl.isNull())
return false;
- SqlQueryPtr result = srcDb->exec(ddl);
+ SqlQueryPtr result;
+ if (attachName.isNull())
+ result = dstDb->exec(ddl);
+ else
+ result = srcDb->exec(ddl); // uses attachName to create object in attached db
+
if (result->isError())
{
notifyError(errorMessage.arg(result->getErrorText()));
@@ -555,28 +559,9 @@ bool DbObjectOrganizer::copySimpleObjectToDb(const QString& name, const QString&
return true;
}
-QSet<QString> DbObjectOrganizer::resolveReferencedTables(const QString& table, const QList<SqliteCreateTablePtr>& parsedTables)
+void DbObjectOrganizer::collectReferencedTables(const QString& table)
{
- QSet<QString> tables = toSet(SchemaResolver::getFkReferencingTables(table, parsedTables));
- for (const QString& fkTable : tables)
- tables += toSet(SchemaResolver::getFkReferencingTables(fkTable, parsedTables));
-
- tables.remove(table); // if it appeared somewhere in the references - we still don't need it here, it's the table we asked by in the first place
- return tables;
-}
-
-void DbObjectOrganizer::collectReferencedTables(const QString& table, const StrHash<SqliteQueryPtr>& allParsedObjects)
-{
- QList<SqliteCreateTablePtr> parsedTables;
- SqliteCreateTablePtr parsedTable;
- for (SqliteQueryPtr& query : allParsedObjects.values())
- {
- parsedTable = query.dynamicCast<SqliteCreateTable>();
- if (parsedTable)
- parsedTables << parsedTable;
- }
-
- QSet<QString> tables = resolveReferencedTables(table, parsedTables);
+ QStringList tables = srcResolver->getFkReferencedTables(table);
for (const QString& refTable : tables)
{
if (!referencedTables.contains(refTable) && !srcTables.contains(refTable))
diff --git a/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.h b/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.h
index 14a4b46..d82efd8 100644
--- a/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.h
+++ b/SQLiteStudio3/coreSQLiteStudio/dbobjectorganizer.h
@@ -85,8 +85,7 @@ class API_EXPORT DbObjectOrganizer : public QObject, public QRunnable, public In
bool copyIndexToDb(const QString& index);
bool copyTriggerToDb(const QString& trigger);
bool copySimpleObjectToDb(const QString& name, const QString& errorMessage, SchemaResolver::ObjectType objectType);
- QSet<QString> resolveReferencedTables(const QString& table, const QList<SqliteCreateTablePtr>& parsedTables);
- void collectReferencedTables(const QString& table, const StrHash<SqliteQueryPtr>& allParsedObjects);
+ void collectReferencedTables(const QString& table);
void collectReferencedIndexes(const QString& table);
void collectReferencedTriggersForTable(const QString& table);
void collectReferencedTriggersForView(const QString& view);
diff --git a/SQLiteStudio3/coreSQLiteStudio/expectedtoken.h b/SQLiteStudio3/coreSQLiteStudio/expectedtoken.h
index 9242dd8..00d82af 100644
--- a/SQLiteStudio3/coreSQLiteStudio/expectedtoken.h
+++ b/SQLiteStudio3/coreSQLiteStudio/expectedtoken.h
@@ -23,15 +23,15 @@ struct API_EXPORT ExpectedToken
VIEW,
DATABASE,
NO_VALUE,
+ STRING,
+ NUMBER,
+ BLOB,
+ OTHER,
KEYWORD,
FUNCTION,
OPERATOR,
COLLATION,
- PRAGMA,
- STRING,
- NUMBER,
- BLOB,
- OTHER
+ PRAGMA
};
/**
diff --git a/SQLiteStudio3/coreSQLiteStudio/exportworker.cpp b/SQLiteStudio3/coreSQLiteStudio/exportworker.cpp
index 8a59495..c7f1059 100644
--- a/SQLiteStudio3/coreSQLiteStudio/exportworker.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/exportworker.cpp
@@ -25,7 +25,7 @@ ExportWorker::~ExportWorker()
void ExportWorker::run()
{
- qDebug() << "ExportWorker thread started. Export mode: " << static_cast<int>(exportMode);
+ //qDebug() << "ExportWorker thread started. Export mode: " << static_cast<int>(exportMode);
bool res = false;
switch (exportMode)
{
@@ -142,6 +142,9 @@ bool ExportWorker::exportQueryResults()
return false;
}
+ int rowIdx = 0;
+ emit finishedStep(rowIdx);
+
SqlResultsRowPtr row;
while (results->hasNext())
{
@@ -151,6 +154,9 @@ bool ExportWorker::exportQueryResults()
logExportFail("exportQueryResultsRow()");
return false;
}
+ if (++rowIdx % 10 == 0)
+ emit finishedStep(rowIdx);
+
if (isInterrupted())
{
diff --git a/SQLiteStudio3/coreSQLiteStudio/exportworker.h b/SQLiteStudio3/coreSQLiteStudio/exportworker.h
index 5e8bef3..a0bcab6 100644
--- a/SQLiteStudio3/coreSQLiteStudio/exportworker.h
+++ b/SQLiteStudio3/coreSQLiteStudio/exportworker.h
@@ -56,6 +56,7 @@ class API_EXPORT ExportWorker : public QObject, public QRunnable
signals:
void finished(bool result, QIODevice* output);
+ void finishedStep(int step);
};
#endif // EXPORTWORKER_H
diff --git a/SQLiteStudio3/coreSQLiteStudio/importworker.cpp b/SQLiteStudio3/coreSQLiteStudio/importworker.cpp
index 1a949a9..c761231 100644
--- a/SQLiteStudio3/coreSQLiteStudio/importworker.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/importworker.cpp
@@ -25,7 +25,8 @@ void ImportWorker::run()
return;
}
- if (!config->skipTransaction && !db->begin())
+ shouldSkipTransaction = config->skipTransaction || db->isTransactionActive();
+ if (!shouldSkipTransaction && !db->begin(config->noDbLock))
{
error(tr("Could not start transaction in order to import a data: %1").arg(db->getErrorText()));
return;
@@ -33,8 +34,8 @@ void ImportWorker::run()
if (!prepareTable())
{
- if (!config->skipTransaction)
- db->rollback();
+ if (!shouldSkipTransaction)
+ db->rollback(config->noDbLock);
return;
}
@@ -42,17 +43,17 @@ void ImportWorker::run()
int rowCount = 0;
if (!importData(rowCount))
{
- if (!config->skipTransaction)
- db->rollback();
+ if (!shouldSkipTransaction)
+ db->rollback(config->noDbLock);
return;
}
- if (!config->skipTransaction && !db->commit())
+ if (!shouldSkipTransaction && !db->commit(config->noDbLock))
{
error(tr("Could not commit transaction for imported data: %1").arg(db->getErrorText()));
- if (!config->skipTransaction)
- db->rollback();
+ if (!shouldSkipTransaction)
+ db->rollback(config->noDbLock);
return;
}
@@ -117,7 +118,7 @@ bool ImportWorker::prepareTable()
colDefs << (wrapObjIfNeeded(columnsFromPlugin[i]) + " " + columnTypesFromPlugin[i]).trimmed();
static const QString ddl = QStringLiteral("CREATE TABLE %1 (%2)");
- Db::Flags flags = config->skipTransaction ? Db::Flag::NO_LOCK : Db::Flag::NONE;
+ Db::Flags flags = config->noDbLock ? Db::Flag::NO_LOCK : Db::Flag::NONE;
SqlQueryPtr result = db->exec(ddl.arg(wrapObjIfNeeded(table), colDefs.join(", ")), flags);
if (result->isError())
{
diff --git a/SQLiteStudio3/coreSQLiteStudio/importworker.h b/SQLiteStudio3/coreSQLiteStudio/importworker.h
index c0912f6..c3ef721 100644
--- a/SQLiteStudio3/coreSQLiteStudio/importworker.h
+++ b/SQLiteStudio3/coreSQLiteStudio/importworker.h
@@ -32,6 +32,7 @@ class ImportWorker : public QObject, public QRunnable
bool interrupted = false;
QMutex interruptMutex;
bool tableCreated = false;
+ bool shouldSkipTransaction = false;
public slots:
void interrupt();
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.cpp
index fff4036..165a5fc 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.cpp
@@ -701,12 +701,15 @@ SqliteCreateTable::Column::Column(const QString &name, SqliteColumnType *type, c
this->constraints.last()->type != SqliteCreateTable::Column::Constraint::NAME_ONLY)
{
SqliteCreateTable::Column::Constraint* last = this->constraints.last();
- last->foreignKey->deferrable = constr->deferrable;
- last->foreignKey->initially = constr->initially;
- delete constr;
-
- // We don't want deleted constr to be added to list. We finish this now.
- continue;
+ if (last->type == Constraint::FOREIGN_KEY)
+ {
+ last->foreignKey->deferrable = constr->deferrable;
+ last->foreignKey->initially = constr->initially;
+ delete constr;
+
+ // We don't want deleted constr to be added to list. We finish this now.
+ continue;
+ }
}
this->constraints << constr;
@@ -870,8 +873,26 @@ TokenList SqliteCreateTable::Column::Constraint::rebuildTokensFromContents()
break;
}
case SqliteCreateTable::Column::Constraint::NULL_:
- case SqliteCreateTable::Column::Constraint::NAME_ONLY:
+ {
+ // Is the default and unofficial. Pass through
+ builder.withKeyword("NULL");
+ break;
+ }
case SqliteCreateTable::Column::Constraint::DEFERRABLE_ONLY:
+ {
+ // Pass through
+ if (deferrable == SqliteDeferrable::NOT_DEFERRABLE)
+ builder.withKeyword("NOT").withSpace();
+ builder.withKeyword("DEFERRABLE");
+ if (initially != SqliteInitially::null)
+ {
+ builder.withSpace().withKeyword("INITIALLY").withSpace();
+ builder.withKeyword(initially == SqliteInitially::DEFERRED ? "DEFERRED" : "IMMEDIATE");
+ }
+ break;
+ }
+ case SqliteCreateTable::Column::Constraint::NAME_ONLY:
+ // The CONSTRAINT <name> clause has already been output
break;
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.h b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.h
index 5d797c1..0507740 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.h
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreatetable.h
@@ -91,13 +91,14 @@ class API_EXPORT SqliteCreateTable : public SqliteQuery, public SqliteDdlWithDbC
GeneratedType generatedType = GeneratedType::null;
SqliteForeignKey* foreignKey = nullptr;
+ // DEFERRABLE_ONLY fields. A DEFERRABLE_ONLY pseudo-constraint following a
+ // a FK is merged to the FK at parse time.
+ SqliteDeferrable deferrable = SqliteDeferrable::null;
+ SqliteInitially initially = SqliteInitially::null;
+
protected:
TokenList rebuildTokensFromContents();
- private:
- SqliteDeferrable deferrable = SqliteDeferrable::null; // only a temporary field for parse time, before merging with actual FK
- SqliteInitially initially = SqliteInitially::null; // only a temporary field for parse time, before merging with actual FK
-
};
typedef QSharedPointer<Constraint> ConstraintPtr;
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.cpp
index 0e11619..36d5852 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.cpp
@@ -4,6 +4,7 @@
#include "parser/statementtokenbuilder.h"
#include "common/global.h"
#include "sqliteindexedcolumn.h"
+#include <QDebug>
SqliteCreateView::SqliteCreateView()
{
@@ -139,3 +140,57 @@ void SqliteCreateView::setObjectName(const QString& name)
{
view = name;
}
+
+TokenList SqliteCreateView::equivalentSelectTokens() const
+{
+ if (columns.size() == 0)
+ return select->tokens;
+
+ SqliteSelect::Core *core = select->coreSelects.first();
+ bool hasStar = std::any_of(core->resultColumns.cbegin(),
+ core->resultColumns.cend(),
+ [](auto col) { return col->star; });
+ bool useCTE = false;
+ if (!hasStar && columns.size() != core->resultColumns.size())
+ {
+ qWarning() << "View with a column list clause and non-matching count of columns in SELECT. "
+ << "Expect an error if result column count does not match column list length.";
+ useCTE = true;
+ }
+ if (hasStar)
+ {
+ qWarning() << "View with a column list clause and SELECT *. "
+ << "Expect an error if result column count does not match column list length.";
+ useCTE = true;
+ }
+ if (useCTE)
+ {
+ StatementTokenBuilder builder;
+ builder.withKeyword("WITH").withSpace().withOther(view).withParLeft();
+ bool first = true;
+ for (SqliteIndexedColumn *column : columns)
+ {
+ if (!first)
+ builder.withOperator(",");
+ first = false;
+ builder.withOther(column->name);
+ }
+ builder.withParRight().withKeyword("AS").withParLeft().withTokens(select->tokens).withParRight()
+ .withKeyword("SELECT").withSpace().withOperator("*").withSpace()
+ .withKeyword("FROM").withSpace().withOther(view);
+ return builder.build();
+ }
+
+ // There are no * in SELECT, and view column list length matches SELECT column list length.
+ // Apply view column names to SELECT as aliases.
+ SqliteSelect* selectCopy = dynamic_cast<SqliteSelect*>(select->clone());
+ QList<SqliteSelect::Core::ResultColumn*> resultColumns = selectCopy->coreSelects.first()->resultColumns;
+ int n = 0;
+ for (SqliteSelect::Core::ResultColumn* column : resultColumns)
+ {
+ column->asKw = true;
+ column->alias = columns.at(n++)->name;
+ }
+ selectCopy->rebuildTokens();
+ return selectCopy->tokens;
+}
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.h b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.h
index 645532c..d90ce7d 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.h
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitecreateview.h
@@ -23,6 +23,7 @@ class API_EXPORT SqliteCreateView : public SqliteQuery, public SqliteDdlWithDbCo
void setTargetDatabase(const QString& database);
QString getObjectName() const;
void setObjectName(const QString& name);
+ TokenList equivalentSelectTokens() const;
bool tempKw = false;
bool temporaryKw = false;
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqliteexpr.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqliteexpr.cpp
index 89c6b9b..7039970 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqliteexpr.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqliteexpr.cpp
@@ -456,6 +456,9 @@ QStringList SqliteExpr::getTablesInStatement()
QStringList SqliteExpr::getDatabasesInStatement()
{
+ if (database.isNull() && !table.isNull() && validDbNames.contains(table, Qt::CaseInsensitive))
+ return getStrListFromValue(table); // it's a "db.", not a "db.table."
+
return getStrListFromValue(database);
}
@@ -494,7 +497,9 @@ TokenList SqliteExpr::getTableTokensInStatement()
TokenList SqliteExpr::getDatabaseTokensInStatement()
{
TokenList list;
- if (!database.isNull())
+ if (database.isNull() && !table.isNull() && validDbNames.contains(table, Qt::CaseInsensitive))
+ list << tokens[0]; // it's a "db.", not a "db.table."
+ else if (!database.isNull())
list << tokens[0];
return list;
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.cpp
index d349a86..90d670b 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.cpp
@@ -2,6 +2,7 @@
#include "../token.h"
#include "../lexer.h"
#include "common/unused.h"
+#include "services/dbmanager.h"
#include <QDebug>
SqliteStatement::SqliteStatement()
@@ -35,6 +36,7 @@ QStringList SqliteStatement::getContextTables(bool checkParent, bool checkChilds
QStringList SqliteStatement::getContextDatabases(bool checkParent, bool checkChilds)
{
+ prepareDbNames();
return getContextDatabases(this, checkParent, checkChilds);
}
@@ -50,6 +52,7 @@ TokenList SqliteStatement::getContextTableTokens(bool checkParent, bool checkChi
TokenList SqliteStatement::getContextDatabaseTokens(bool checkParent, bool checkChilds)
{
+ prepareDbNames();
return getContextDatabaseTokens(this, checkParent, checkChilds);
}
@@ -125,7 +128,10 @@ QStringList SqliteStatement::getContextDatabases(SqliteStatement *caller, bool c
{
QStringList results = getDatabasesInStatement();
for (SqliteStatement* stmt : getContextStatements(caller, checkParent, checkChilds))
+ {
+ stmt->validDbNames = this->validDbNames;
results += stmt->getContextDatabases(this, checkParent, checkChilds);
+ }
return results;
}
@@ -152,7 +158,10 @@ TokenList SqliteStatement::getContextDatabaseTokens(SqliteStatement *caller, boo
{
TokenList results = getDatabaseTokensInStatement();
for (SqliteStatement* stmt : getContextStatements(caller, checkParent, checkChilds))
+ {
+ stmt->validDbNames = this->validDbNames;
results += stmt->getContextDatabaseTokens(this, checkParent, checkChilds);
+ }
return results;
}
@@ -236,6 +245,11 @@ QList<SqliteStatement *> SqliteStatement::getContextStatements(SqliteStatement *
return results;
}
+void SqliteStatement::prepareDbNames()
+{
+ validDbNames = DBLIST->getValidDbNames();
+}
+
TokenList SqliteStatement::extractPrintableTokens(const TokenList &tokens, bool skipMeaningless)
{
TokenList list;
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.h b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.h
index 167321f..794b6de 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.h
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/ast/sqlitestatement.h
@@ -333,8 +333,16 @@ class API_EXPORT SqliteStatement : public QObject
*/
TokenPtr dbTokenForFullObjects;
+ /**
+ * @brief List of database names as seen in the side Database List.
+ * It is resoled at top-level statement being queried for databases and then it's propagated down to all child statements.
+ * It helps to identify whether the xyz in "xyz." is a table or a database prefix.
+ */
+ QStringList validDbNames;
+
private:
QList<SqliteStatement*> getContextStatements(SqliteStatement* caller, bool checkParent, bool checkChilds);
+ void prepareDbNames();
};
#endif // SQLITESTATEMENT_H
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/compile_lemon.sh b/SQLiteStudio3/coreSQLiteStudio/parser/compile_lemon.sh
new file mode 100755
index 0000000..b93c592
--- /dev/null
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/compile_lemon.sh
@@ -0,0 +1,6 @@
+#!/bin/sh
+LEMON=~/lemon
+GCC=gcc
+
+$GCC -o $LEMON lemon.c
+
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/parser.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/parser.cpp
index b80d45a..aa99ee1 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/parser.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/parser.cpp
@@ -214,7 +214,8 @@ void Parser::expectedTokenLookup(void* pParser)
Token::CTX_ALIAS, Token::CTX_TABLE_NEW, Token::CTX_INDEX_NEW, Token::CTX_TRIGGER_NEW,
Token::CTX_VIEW_NEW, Token::CTX_COLUMN_NEW, Token::CTX_TRANSACTION,
Token::CTX_CONSTRAINT, Token::CTX_COLUMN_TYPE, Token::CTX_OLD_KW, Token::CTX_NEW_KW,
- Token::CTX_ROWID_KW, Token::CTX_STRICT_KW, Token::INVALID
+ Token::CTX_ROWID_KW, Token::CTX_STRICT_KW, Token::INVALID,
+ Token::BLOB, Token::STRING, Token::FLOAT, Token::INTEGER
});
for (TokenPtr token : tokenSet)
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/run_lemon.sh b/SQLiteStudio3/coreSQLiteStudio/parser/run_lemon.sh
index d42f0c1..9ed260c 100755
--- a/SQLiteStudio3/coreSQLiteStudio/parser/run_lemon.sh
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/run_lemon.sh
@@ -1,5 +1,5 @@
#!/bin/sh
#lemon -l -q -s sqlite3_parse.y
-lemon -l -q sqlite3_parse.y
+~/lemon -l -q sqlite3_parse.y
mv sqlite3_parse.c sqlite3_parse.cpp
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.cpp b/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.cpp
index 7be06fb..be0f9fc 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.cpp
@@ -112,80 +112,80 @@
** defined, then do no error processing.
*/
#define YYCODETYPE unsigned short int
-#define YYNOCODE 328
+#define YYNOCODE 329
#define YYACTIONTYPE unsigned short int
#define YYWILDCARD 80
#define sqlite3_parseTOKENTYPE Token*
typedef union {
int yyinit;
sqlite3_parseTOKENTYPE yy0;
- SqliteCreateTable::Column* yy3;
- SqliteFilterOver::Over* yy11;
- SqliteWith::CommonTableExpression::AsMode* yy21;
- ParserResultColumnList* yy27;
- SqliteSortOrder* yy35;
- SqliteFilterOver::Filter* yy39;
- SqliteQuery* yy41;
- ParserDeferSubClause* yy53;
- SqliteForeignKey::Condition::Reaction* yy106;
- ParserOtherSourceList* yy107;
- SqliteIndexedColumn* yy110;
- ParserCreateTableConstraintList* yy115;
- SqliteCreateTrigger::Time* yy120;
- int* yy130;
- SqliteConflictAlgo* yy136;
- SqliteSelect::CompoundOperator* yy142;
- SqliteWindowDefinition::Window::Frame::RangeOrRows* yy143;
- SqliteWith::CommonTableExpression* yy146;
- SqliteWindowDefinition::Window::Frame* yy149;
- ParserFkConditionList* yy156;
- SqliteWith* yy161;
- SqliteWindowDefinition::Window* yy162;
- ParserCteList* yy164;
- QStringList* yy173;
- SqliteFilterOver* yy181;
- SqliteExpr* yy186;
- SqliteForeignKey::Condition* yy205;
- SqliteSelect::Core::JoinConstraint* yy215;
- bool* yy225;
- ParserOrderByList* yy226;
- SqliteWindowDefinition::Window::Frame::Exclude* yy237;
- ParserQueryList* yy240;
- SqliteCreateTrigger::Event* yy259;
- SqliteColumnType* yy267;
- SqliteExpr::LikeOp* yy274;
- SqliteWindowDefinition::Window::Frame::Bound* yy285;
- SqliteSelect* yy297;
- ParserIndexedBy* yy300;
- ParserStubInsertOrReplace* yy308;
- SqliteNulls* yy315;
- QString* yy319;
- ParserCreateTableColumnConstraintList* yy323;
- SqliteUpsert* yy332;
- SqliteLimit* yy360;
- SqliteSelect::Core* yy378;
- ParserTermOrLiteral* yy380;
- ParserCreateTableColumnList* yy390;
- QVariant* yy393;
- ParserFullName* yy396;
- SqliteCreateTable::Constraint* yy400;
- SqliteCreateTable::Column::Constraint* yy448;
- SqliteSelect::Core::JoinOp* yy449;
- ParserCreateTableOptionList* yy455;
- SqliteCreateTrigger::Scope* yy456;
- ParserStubExplain* yy499;
- ParserStubTransDetails* yy512;
- ParserExprNestedList* yy522;
- ParserWindowDefList* yy525;
- SqliteSelect::Core::JoinSource* yy553;
- SqliteWindowDefinition* yy562;
- SqliteSelect::Core::SingleSource* yy595;
- SqliteInitially* yy612;
- ParserExprList* yy615;
- ParserSetValueList* yy621;
- ParserIndexedColumnList* yy627;
- ParserStubAlias* yy628;
- ParserStubCreateTableOption* yy629;
+ SqliteLimit* yy4;
+ SqliteWindowDefinition::Window* yy14;
+ SqliteUpsert* yy16;
+ ParserCteList* yy17;
+ SqliteWindowDefinition::Window::Frame::RangeOrRows* yy34;
+ bool* yy35;
+ ParserExprNestedList* yy54;
+ ParserFkConditionList* yy56;
+ SqliteCreateTable::Column::Constraint* yy64;
+ SqliteConflictAlgo* yy66;
+ SqliteSelect* yy73;
+ SqliteWindowDefinition* yy74;
+ SqliteNulls* yy99;
+ ParserStubTransDetails* yy100;
+ SqliteExpr::LikeOp* yy104;
+ SqliteCreateTable::Column* yy115;
+ SqliteCreateTable::Constraint* yy166;
+ SqliteExpr* yy176;
+ ParserOtherSourceList* yy195;
+ ParserCreateTableOptionList* yy217;
+ ParserDeferSubClause* yy218;
+ ParserIndexedBy* yy224;
+ SqliteFilterOver::Over* yy231;
+ ParserCreateTableColumnList* yy234;
+ QString* yy255;
+ ParserCreateTableColumnConstraintList* yy259;
+ SqliteFilterOver::Filter* yy269;
+ ParserStubAlias* yy280;
+ ParserStubInsertOrReplace* yy281;
+ SqliteWith* yy321;
+ SqliteSelect::Core::JoinSource* yy335;
+ QStringList* yy336;
+ SqliteWindowDefinition::Window::Frame::Exclude* yy337;
+ SqliteWith::CommonTableExpression* yy366;
+ SqliteWith::CommonTableExpression::AsMode* yy383;
+ SqliteSelect::Core::SingleSource* yy393;
+ SqliteWindowDefinition::Window::Frame::Bound* yy394;
+ SqliteCreateTrigger::Scope* yy403;
+ SqliteCreateTrigger::Event* yy407;
+ ParserResultColumnList* yy421;
+ SqliteSelect::Core::JoinConstraint* yy423;
+ SqliteSelect::Core* yy438;
+ ParserCreateTableConstraintList* yy445;
+ SqliteSelect::Core::JoinOp* yy461;
+ SqliteFilterOver* yy487;
+ SqliteForeignKey::Condition::Reaction* yy488;
+ ParserOrderByList* yy499;
+ ParserFullName* yy520;
+ ParserIndexedColumnList* yy527;
+ SqliteInitially* yy536;
+ SqliteIndexedColumn* yy540;
+ ParserTermOrLiteral* yy542;
+ ParserWindowDefList* yy555;
+ int* yy562;
+ ParserExprList* yy567;
+ ParserStubExplain* yy571;
+ SqliteSelect::CompoundOperator* yy574;
+ ParserQueryList* yy575;
+ SqliteWindowDefinition::Window::Frame* yy585;
+ SqliteForeignKey::Condition* yy587;
+ SqliteColumnType* yy601;
+ ParserStubCreateTableOption* yy607;
+ SqliteCreateTrigger::Time* yy612;
+ ParserSetValueList* yy617;
+ QVariant* yy629;
+ SqliteQuery* yy635;
+ SqliteSortOrder* yy645;
} YYMINORTYPE;
#ifndef YYSTACKDEPTH
#define YYSTACKDEPTH 100
@@ -194,8 +194,8 @@ typedef union {
#define sqlite3_parseARG_PDECL ,ParserContext* parserContext
#define sqlite3_parseARG_FETCH ParserContext* parserContext = yypParser->parserContext
#define sqlite3_parseARG_STORE yypParser->parserContext = parserContext
-#define YYNSTATE 870
-#define YYNRULE 487
+#define YYNSTATE 871
+#define YYNRULE 490
#define YYFALLBACK 1
#define YY_NO_ACTION (YYNSTATE+YYNRULE+2)
#define YY_ACCEPT_ACTION (YYNSTATE+YYNRULE+1)
@@ -267,778 +267,775 @@ static const YYMINORTYPE yyzerominor = { 0 };
** shifting non-terminals after a reduce.
** yy_default[] Default action for each state.
*/
-#define YY_ACTTAB_COUNT (2866)
+#define YY_ACTTAB_COUNT (2846)
static const YYACTIONTYPE yy_action[] = {
- /* 0 */ 530, 162, 431, 771, 456, 453, 452, 27, 67, 68,
- /* 10 */ 529, 282, 521, 770, 818, 818, 65, 65, 66, 66,
- /* 20 */ 66, 66, 451, 64, 64, 64, 64, 63, 63, 62,
- /* 30 */ 62, 62, 61, 59, 263, 464, 1230, 807, 67, 68,
- /* 40 */ 529, 282, 58, 116, 818, 818, 65, 65, 66, 66,
- /* 50 */ 66, 66, 526, 64, 64, 64, 64, 63, 63, 62,
- /* 60 */ 62, 62, 61, 59, 263, 681, 1280, 62, 62, 62,
- /* 70 */ 61, 59, 263, 808, 432, 66, 66, 66, 66, 56,
+ /* 0 */ 531, 62, 62, 62, 61, 59, 263, 27, 67, 68,
+ /* 10 */ 530, 283, 522, 694, 819, 819, 65, 65, 66, 66,
+ /* 20 */ 66, 66, 837, 64, 64, 64, 64, 63, 63, 62,
+ /* 30 */ 62, 62, 61, 59, 263, 465, 1234, 808, 67, 68,
+ /* 40 */ 530, 283, 58, 135, 819, 819, 65, 65, 66, 66,
+ /* 50 */ 66, 66, 527, 64, 64, 64, 64, 63, 63, 62,
+ /* 60 */ 62, 62, 61, 59, 263, 381, 1284, 282, 281, 796,
+ /* 70 */ 659, 261, 78, 809, 194, 66, 66, 66, 66, 56,
/* 80 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 90 */ 59, 263, 834, 862, 14, 835, 53, 54, 715, 704,
- /* 100 */ 704, 353, 828, 619, 55, 1042, 508, 633, 295, 781,
- /* 110 */ 530, 299, 2, 1042, 343, 861, 861, 816, 1042, 354,
- /* 120 */ 867, 518, 521, 830, 859, 829, 230, 672, 673, 833,
- /* 130 */ 1108, 821, 324, 861, 528, 327, 816, 832, 831, 830,
- /* 140 */ 406, 1042, 39, 143, 608, 80, 862, 128, 515, 291,
- /* 150 */ 472, 265, 709, 708, 1042, 301, 1042, 1042, 828, 585,
- /* 160 */ 1042, 290, 526, 366, 368, 1042, 1042, 1042, 1042, 1042,
- /* 170 */ 1042, 816, 861, 609, 816, 611, 806, 12, 610, 364,
- /* 180 */ 560, 829, 230, 808, 510, 506, 163, 351, 1042, 56,
- /* 190 */ 528, 782, 132, 82, 861, 371, 587, 365, 21, 428,
- /* 200 */ 561, 562, 367, 183, 805, 72, 53, 54, 109, 89,
- /* 210 */ 723, 81, 497, 127, 55, 1108, 860, 859, 483, 468,
- /* 220 */ 530, 560, 2, 1108, 862, 297, 448, 816, 1108, 724,
- /* 230 */ 791, 518, 521, 830, 859, 861, 107, 809, 498, 833,
- /* 240 */ 381, 561, 414, 8, 723, 172, 816, 832, 831, 830,
- /* 250 */ 369, 1108, 181, 745, 821, 1059, 1059, 141, 72, 52,
- /* 260 */ 758, 50, 809, 723, 1108, 502, 1108, 1108, 688, 860,
- /* 270 */ 859, 861, 526, 563, 798, 1108, 1108, 1108, 1108, 861,
- /* 280 */ 1108, 816, 724, 78, 816, 194, 806, 12, 386, 862,
- /* 290 */ 734, 382, 687, 808, 334, 79, 809, 723, 1108, 56,
+ /* 90 */ 59, 263, 835, 863, 23, 836, 53, 54, 716, 615,
+ /* 100 */ 831, 796, 520, 261, 55, 1043, 834, 634, 801, 800,
+ /* 110 */ 531, 829, 2, 1043, 833, 832, 831, 817, 1043, 840,
+ /* 120 */ 752, 519, 522, 831, 860, 862, 355, 666, 460, 834,
+ /* 130 */ 1109, 251, 250, 249, 830, 223, 817, 833, 832, 831,
+ /* 140 */ 862, 1043, 752, 529, 609, 80, 863, 128, 752, 292,
+ /* 150 */ 863, 265, 868, 412, 1043, 432, 1043, 1043, 829, 367,
+ /* 160 */ 1043, 291, 527, 163, 369, 1043, 1043, 1043, 1043, 1043,
+ /* 170 */ 1043, 817, 862, 610, 817, 612, 807, 12, 611, 141,
+ /* 180 */ 82, 830, 230, 809, 620, 308, 443, 318, 1043, 56,
+ /* 190 */ 529, 863, 132, 862, 776, 285, 474, 366, 325, 21,
+ /* 200 */ 428, 328, 368, 183, 806, 72, 53, 54, 109, 89,
+ /* 210 */ 724, 81, 810, 127, 55, 1109, 861, 860, 484, 469,
+ /* 220 */ 531, 162, 2, 1109, 457, 454, 453, 817, 1109, 725,
+ /* 230 */ 286, 519, 522, 831, 860, 341, 513, 810, 779, 834,
+ /* 240 */ 561, 382, 452, 523, 724, 365, 817, 833, 832, 831,
+ /* 250 */ 370, 1109, 181, 340, 862, 1060, 1060, 116, 72, 74,
+ /* 260 */ 562, 563, 113, 724, 1109, 387, 1109, 1109, 287, 861,
+ /* 270 */ 860, 810, 527, 861, 860, 1109, 1109, 1109, 1109, 682,
+ /* 280 */ 1109, 817, 725, 672, 817, 73, 807, 12, 407, 804,
+ /* 290 */ 803, 383, 863, 809, 501, 747, 4, 724, 1109, 56,
/* 300 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 310 */ 59, 263, 751, 858, 415, 798, 53, 54, 790, 614,
- /* 320 */ 856, 722, 828, 116, 55, 1093, 742, 167, 413, 857,
- /* 330 */ 469, 173, 2, 1093, 751, 42, 861, 816, 1093, 809,
- /* 340 */ 751, 518, 821, 830, 859, 829, 230, 860, 859, 833,
- /* 350 */ 1358, 190, 535, 3, 528, 487, 816, 832, 831, 830,
- /* 360 */ 815, 1093, 711, 759, 809, 721, 717, 58, 122, 505,
- /* 370 */ 522, 500, 746, 4, 1093, 817, 1093, 1093, 767, 828,
- /* 380 */ 1197, 1197, 483, 470, 600, 1093, 828, 1093, 1093, 601,
- /* 390 */ 1093, 816, 91, 861, 816, 815, 806, 12, 809, 44,
- /* 400 */ 861, 113, 829, 215, 381, 307, 442, 317, 1093, 829,
- /* 410 */ 123, 528, 860, 859, 1200, 284, 473, 423, 528, 67,
- /* 420 */ 68, 529, 282, 1197, 1197, 818, 818, 65, 65, 66,
- /* 430 */ 66, 66, 66, 74, 64, 64, 64, 64, 63, 63,
+ /* 310 */ 59, 263, 344, 461, 861, 860, 53, 54, 61, 59,
+ /* 320 */ 263, 627, 829, 107, 55, 1094, 354, 816, 413, 671,
+ /* 330 */ 470, 264, 2, 1094, 564, 799, 862, 817, 1094, 822,
+ /* 340 */ 862, 519, 822, 831, 860, 830, 230, 498, 473, 834,
+ /* 350 */ 710, 709, 818, 503, 529, 658, 817, 833, 832, 831,
+ /* 360 */ 364, 1094, 816, 859, 799, 644, 92, 862, 122, 862,
+ /* 370 */ 857, 673, 674, 499, 1094, 829, 1094, 1094, 829, 858,
+ /* 380 */ 1199, 1199, 484, 471, 142, 1094, 503, 1094, 1094, 862,
+ /* 390 */ 1094, 817, 862, 772, 817, 759, 807, 12, 830, 201,
+ /* 400 */ 862, 830, 215, 771, 1, 382, 177, 529, 1094, 828,
+ /* 410 */ 529, 705, 705, 863, 1204, 861, 860, 790, 399, 67,
+ /* 420 */ 68, 530, 283, 1199, 1199, 819, 819, 65, 65, 66,
+ /* 430 */ 66, 66, 66, 822, 64, 64, 64, 64, 63, 63,
/* 440 */ 62, 62, 62, 61, 59, 263, 63, 63, 62, 62,
- /* 450 */ 62, 61, 59, 263, 800, 799, 172, 332, 504, 73,
- /* 460 */ 626, 775, 116, 1197, 1197, 821, 389, 247, 775, 67,
- /* 470 */ 68, 529, 282, 69, 264, 818, 818, 65, 65, 66,
- /* 480 */ 66, 66, 66, 412, 64, 64, 64, 64, 63, 63,
- /* 490 */ 62, 62, 62, 61, 59, 263, 496, 58, 142, 753,
- /* 500 */ 588, 734, 67, 68, 529, 282, 1197, 1197, 818, 818,
- /* 510 */ 65, 65, 66, 66, 66, 66, 862, 64, 64, 64,
- /* 520 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 788,
- /* 530 */ 449, 703, 828, 830, 340, 116, 372, 1307, 177, 833,
- /* 540 */ 657, 787, 1307, 45, 505, 363, 861, 832, 831, 830,
- /* 550 */ 643, 92, 339, 254, 861, 829, 230, 407, 803, 802,
- /* 560 */ 285, 1197, 1197, 380, 528, 342, 699, 795, 658, 261,
- /* 570 */ 1200, 81, 1200, 66, 66, 66, 66, 40, 64, 64,
+ /* 450 */ 62, 61, 59, 263, 39, 143, 172, 163, 776, 431,
+ /* 460 */ 506, 776, 822, 1199, 1199, 822, 504, 769, 254, 67,
+ /* 470 */ 68, 530, 283, 69, 821, 819, 819, 65, 65, 66,
+ /* 480 */ 66, 66, 66, 91, 64, 64, 64, 64, 63, 63,
+ /* 490 */ 62, 62, 62, 61, 59, 263, 497, 449, 760, 754,
+ /* 500 */ 768, 735, 67, 68, 530, 283, 1199, 1199, 819, 819,
+ /* 510 */ 65, 65, 66, 66, 66, 66, 589, 64, 64, 64,
+ /* 520 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 789,
+ /* 530 */ 345, 586, 782, 863, 561, 810, 861, 860, 603, 604,
+ /* 540 */ 425, 788, 176, 45, 862, 8, 57, 172, 862, 729,
+ /* 550 */ 388, 14, 373, 1311, 562, 414, 822, 863, 1311, 387,
+ /* 560 */ 810, 1199, 1199, 81, 728, 335, 689, 372, 588, 813,
+ /* 570 */ 1204, 516, 1204, 66, 66, 66, 66, 40, 64, 64,
/* 580 */ 64, 64, 63, 63, 62, 62, 62, 61, 59, 263,
- /* 590 */ 693, 862, 483, 484, 281, 280, 862, 1201, 286, 836,
- /* 600 */ 67, 68, 529, 282, 1197, 1197, 818, 818, 65, 65,
- /* 610 */ 66, 66, 66, 66, 381, 64, 64, 64, 64, 63,
- /* 620 */ 63, 62, 62, 62, 61, 59, 263, 862, 1, 751,
- /* 630 */ 430, 141, 798, 827, 812, 800, 799, 788, 647, 860,
- /* 640 */ 859, 677, 328, 1197, 1197, 861, 409, 492, 648, 787,
- /* 650 */ 87, 751, 67, 68, 529, 282, 861, 751, 818, 818,
- /* 660 */ 65, 65, 66, 66, 66, 66, 862, 64, 64, 64,
- /* 670 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 251,
- /* 680 */ 250, 249, 67, 68, 529, 282, 1197, 1197, 818, 818,
- /* 690 */ 65, 65, 66, 66, 66, 66, 176, 64, 64, 64,
- /* 700 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 764,
- /* 710 */ 502, 135, 777, 656, 860, 859, 657, 1266, 162, 860,
- /* 720 */ 859, 456, 453, 452, 861, 811, 840, 92, 843, 357,
- /* 730 */ 861, 350, 764, 255, 707, 531, 471, 841, 163, 451,
- /* 740 */ 839, 684, 861, 584, 584, 467, 746, 4, 665, 459,
- /* 750 */ 860, 859, 271, 1201, 644, 1201, 862, 683, 67, 68,
- /* 760 */ 529, 282, 23, 491, 818, 818, 65, 65, 66, 66,
- /* 770 */ 66, 66, 486, 64, 64, 64, 64, 63, 63, 62,
- /* 780 */ 62, 62, 61, 59, 263, 67, 68, 529, 282, 860,
- /* 790 */ 859, 818, 818, 65, 65, 66, 66, 66, 66, 751,
+ /* 590 */ 688, 863, 735, 296, 810, 276, 300, 1205, 586, 607,
+ /* 600 */ 67, 68, 530, 283, 1199, 1199, 819, 819, 65, 65,
+ /* 610 */ 66, 66, 66, 66, 752, 64, 64, 64, 64, 63,
+ /* 620 */ 63, 62, 62, 62, 61, 59, 263, 141, 415, 799,
+ /* 630 */ 685, 417, 493, 863, 372, 587, 752, 658, 422, 863,
+ /* 640 */ 302, 862, 752, 1199, 1199, 862, 684, 542, 92, 585,
+ /* 650 */ 585, 862, 67, 68, 530, 283, 861, 860, 819, 819,
+ /* 660 */ 65, 65, 66, 66, 66, 66, 812, 64, 64, 64,
+ /* 670 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 811,
+ /* 680 */ 861, 860, 67, 68, 530, 283, 1199, 1199, 819, 819,
+ /* 690 */ 65, 65, 66, 66, 66, 66, 197, 64, 64, 64,
+ /* 700 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 765,
+ /* 710 */ 298, 844, 805, 657, 861, 860, 658, 1270, 162, 411,
+ /* 720 */ 847, 457, 454, 453, 844, 862, 841, 92, 815, 42,
+ /* 730 */ 862, 532, 765, 842, 1362, 190, 536, 3, 862, 452,
+ /* 740 */ 118, 791, 468, 747, 4, 723, 116, 863, 492, 488,
+ /* 750 */ 599, 167, 272, 1205, 645, 1205, 861, 860, 67, 68,
+ /* 760 */ 530, 283, 861, 860, 819, 819, 65, 65, 66, 66,
+ /* 770 */ 66, 66, 794, 64, 64, 64, 64, 63, 63, 62,
+ /* 780 */ 62, 62, 61, 59, 263, 67, 68, 530, 283, 722,
+ /* 790 */ 718, 819, 819, 65, 65, 66, 66, 66, 66, 869,
/* 800 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 810 */ 59, 263, 530, 1266, 866, 862, 636, 485, 344, 534,
- /* 820 */ 457, 751, 503, 768, 521, 344, 180, 751, 597, 466,
- /* 830 */ 633, 697, 861, 482, 419, 67, 68, 529, 282, 861,
- /* 840 */ 386, 818, 818, 65, 65, 66, 66, 66, 66, 810,
+ /* 810 */ 59, 263, 531, 1270, 345, 863, 355, 599, 835, 345,
+ /* 820 */ 458, 836, 822, 598, 522, 801, 800, 483, 862, 419,
+ /* 830 */ 862, 589, 863, 862, 822, 67, 68, 530, 283, 349,
+ /* 840 */ 822, 819, 819, 65, 65, 66, 66, 66, 66, 822,
/* 850 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 860 */ 59, 263, 821, 828, 526, 342, 699, 570, 80, 401,
- /* 870 */ 353, 122, 119, 61, 59, 263, 842, 861, 585, 860,
- /* 880 */ 859, 81, 744, 376, 861, 808, 829, 223, 692, 481,
- /* 890 */ 376, 56, 135, 259, 804, 528, 569, 592, 568, 325,
- /* 900 */ 283, 567, 633, 326, 965, 520, 803, 802, 53, 54,
- /* 910 */ 22, 246, 245, 861, 371, 586, 55, 179, 126, 341,
- /* 920 */ 462, 336, 461, 164, 2, 1207, 537, 71, 57, 816,
- /* 930 */ 602, 603, 425, 518, 79, 830, 859, 334, 830, 608,
- /* 940 */ 80, 833, 588, 165, 833, 775, 793, 1215, 816, 832,
- /* 950 */ 831, 830, 832, 831, 830, 795, 519, 261, 197, 862,
- /* 960 */ 789, 438, 1202, 354, 1315, 1315, 173, 690, 609, 689,
- /* 970 */ 611, 255, 707, 610, 471, 613, 172, 861, 372, 1306,
- /* 980 */ 798, 293, 821, 816, 1306, 821, 816, 792, 806, 12,
- /* 990 */ 67, 68, 529, 282, 429, 861, 818, 818, 65, 65,
- /* 1000 */ 66, 66, 66, 66, 435, 64, 64, 64, 64, 63,
- /* 1010 */ 63, 62, 62, 62, 61, 59, 263, 67, 68, 529,
- /* 1020 */ 282, 734, 81, 818, 818, 65, 65, 66, 66, 66,
- /* 1030 */ 66, 780, 64, 64, 64, 64, 63, 63, 62, 62,
- /* 1040 */ 62, 61, 59, 263, 67, 68, 529, 282, 662, 661,
- /* 1050 */ 818, 818, 65, 65, 66, 66, 66, 66, 1251, 64,
+ /* 860 */ 59, 263, 822, 829, 527, 122, 845, 373, 1310, 401,
+ /* 870 */ 861, 860, 119, 1310, 348, 829, 354, 862, 745, 377,
+ /* 880 */ 793, 81, 789, 482, 377, 809, 830, 215, 693, 862,
+ /* 890 */ 862, 56, 593, 259, 788, 529, 704, 256, 830, 123,
+ /* 900 */ 255, 708, 634, 472, 966, 743, 781, 529, 53, 54,
+ /* 910 */ 173, 246, 245, 58, 736, 406, 55, 179, 126, 342,
+ /* 920 */ 463, 337, 462, 164, 2, 1211, 517, 71, 779, 817,
+ /* 930 */ 343, 700, 256, 519, 90, 831, 860, 335, 831, 609,
+ /* 940 */ 80, 834, 1219, 698, 834, 822, 776, 505, 817, 833,
+ /* 950 */ 832, 831, 833, 832, 831, 861, 860, 822, 776, 863,
+ /* 960 */ 506, 717, 1206, 822, 1319, 1319, 838, 783, 610, 785,
+ /* 970 */ 612, 780, 822, 611, 795, 664, 172, 343, 700, 196,
+ /* 980 */ 294, 347, 256, 817, 754, 822, 817, 777, 807, 12,
+ /* 990 */ 67, 68, 530, 283, 862, 429, 819, 819, 65, 65,
+ /* 1000 */ 66, 66, 66, 66, 1208, 64, 64, 64, 64, 63,
+ /* 1010 */ 63, 62, 62, 62, 61, 59, 263, 67, 68, 530,
+ /* 1020 */ 283, 735, 775, 819, 819, 65, 65, 66, 66, 66,
+ /* 1030 */ 66, 508, 64, 64, 64, 64, 63, 63, 62, 62,
+ /* 1040 */ 62, 61, 59, 263, 67, 68, 530, 283, 47, 752,
+ /* 1050 */ 819, 819, 65, 65, 66, 66, 66, 66, 355, 64,
/* 1060 */ 64, 64, 64, 63, 63, 62, 62, 62, 61, 59,
- /* 1070 */ 263, 779, 512, 566, 778, 639, 639, 870, 67, 68,
- /* 1080 */ 529, 282, 860, 859, 818, 818, 65, 65, 66, 66,
+ /* 1070 */ 263, 752, 862, 567, 46, 640, 640, 752, 67, 68,
+ /* 1080 */ 530, 283, 861, 860, 819, 819, 65, 65, 66, 66,
/* 1090 */ 66, 66, 51, 64, 64, 64, 64, 63, 63, 62,
- /* 1100 */ 62, 62, 61, 59, 263, 821, 411, 794, 862, 67,
- /* 1110 */ 68, 529, 282, 118, 698, 818, 818, 65, 65, 66,
- /* 1120 */ 66, 66, 66, 437, 64, 64, 64, 64, 63, 63,
- /* 1130 */ 62, 62, 62, 61, 59, 263, 834, 861, 862, 835,
- /* 1140 */ 196, 67, 68, 529, 282, 696, 48, 818, 818, 65,
- /* 1150 */ 65, 66, 66, 66, 66, 776, 64, 64, 64, 64,
- /* 1160 */ 63, 63, 62, 62, 62, 61, 59, 263, 1204, 869,
- /* 1170 */ 3, 436, 67, 68, 529, 282, 173, 679, 818, 818,
- /* 1180 */ 65, 65, 66, 66, 66, 66, 868, 64, 64, 64,
- /* 1190 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 774,
- /* 1200 */ 267, 862, 622, 67, 68, 529, 282, 173, 195, 818,
- /* 1210 */ 818, 65, 65, 66, 66, 66, 66, 735, 64, 64,
+ /* 1100 */ 62, 62, 61, 59, 263, 390, 247, 509, 863, 67,
+ /* 1110 */ 68, 530, 283, 746, 699, 819, 819, 65, 65, 66,
+ /* 1120 */ 66, 66, 66, 438, 64, 64, 64, 64, 63, 63,
+ /* 1130 */ 62, 62, 62, 61, 59, 263, 44, 862, 863, 20,
+ /* 1140 */ 863, 67, 68, 530, 283, 697, 48, 819, 819, 65,
+ /* 1150 */ 65, 66, 66, 66, 66, 79, 64, 64, 64, 64,
+ /* 1160 */ 63, 63, 62, 62, 62, 61, 59, 263, 255, 708,
+ /* 1170 */ 792, 472, 67, 68, 530, 283, 44, 680, 819, 819,
+ /* 1180 */ 65, 65, 66, 66, 66, 66, 507, 64, 64, 64,
+ /* 1190 */ 64, 63, 63, 62, 62, 62, 61, 59, 263, 117,
+ /* 1200 */ 268, 436, 863, 67, 68, 530, 283, 863, 195, 819,
+ /* 1210 */ 819, 65, 65, 66, 66, 66, 66, 77, 64, 64,
/* 1220 */ 64, 64, 63, 63, 62, 62, 62, 61, 59, 263,
- /* 1230 */ 507, 860, 859, 309, 67, 68, 529, 282, 44, 331,
- /* 1240 */ 818, 818, 65, 65, 66, 66, 66, 66, 862, 64,
+ /* 1230 */ 502, 861, 860, 712, 67, 68, 530, 283, 58, 332,
+ /* 1240 */ 819, 819, 65, 65, 66, 66, 66, 66, 863, 64,
/* 1250 */ 64, 64, 64, 63, 63, 62, 62, 62, 61, 59,
- /* 1260 */ 263, 860, 859, 671, 729, 862, 67, 68, 529, 282,
- /* 1270 */ 720, 28, 818, 818, 65, 65, 66, 66, 66, 66,
- /* 1280 */ 735, 64, 64, 64, 64, 63, 63, 62, 62, 62,
- /* 1290 */ 61, 59, 263, 460, 1281, 67, 68, 529, 282, 862,
- /* 1300 */ 719, 818, 818, 65, 65, 66, 66, 66, 66, 670,
+ /* 1260 */ 263, 861, 860, 861, 860, 767, 67, 68, 530, 283,
+ /* 1270 */ 721, 28, 819, 819, 65, 65, 66, 66, 66, 66,
+ /* 1280 */ 736, 64, 64, 64, 64, 63, 63, 62, 62, 62,
+ /* 1290 */ 61, 59, 263, 19, 1285, 67, 68, 530, 283, 737,
+ /* 1300 */ 720, 819, 819, 65, 65, 66, 66, 66, 66, 864,
/* 1310 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 1320 */ 59, 263, 530, 1279, 860, 859, 304, 726, 320, 354,
- /* 1330 */ 735, 44, 269, 81, 521, 837, 47, 494, 67, 68,
- /* 1340 */ 529, 282, 861, 861, 818, 818, 65, 65, 66, 66,
- /* 1350 */ 66, 66, 862, 64, 64, 64, 64, 63, 63, 62,
- /* 1360 */ 62, 62, 61, 59, 263, 598, 46, 828, 530, 606,
- /* 1370 */ 828, 860, 859, 590, 526, 509, 20, 716, 373, 517,
- /* 1380 */ 521, 861, 554, 494, 861, 821, 862, 493, 860, 859,
- /* 1390 */ 829, 230, 828, 829, 230, 808, 843, 256, 399, 528,
- /* 1400 */ 501, 56, 528, 6, 862, 846, 861, 437, 44, 986,
- /* 1410 */ 861, 112, 117, 122, 645, 829, 215, 122, 53, 54,
- /* 1420 */ 526, 861, 860, 859, 528, 77, 55, 408, 417, 862,
- /* 1430 */ 483, 474, 598, 493, 2, 751, 862, 766, 516, 816,
- /* 1440 */ 778, 808, 861, 518, 513, 830, 859, 56, 554, 381,
- /* 1450 */ 530, 833, 381, 499, 539, 828, 441, 751, 816, 832,
- /* 1460 */ 831, 830, 521, 751, 53, 54, 22, 862, 861, 861,
- /* 1470 */ 625, 629, 55, 689, 775, 860, 859, 862, 829, 215,
- /* 1480 */ 2, 864, 122, 19, 266, 816, 739, 528, 551, 518,
- /* 1490 */ 761, 830, 859, 816, 862, 861, 816, 833, 806, 12,
- /* 1500 */ 861, 828, 526, 548, 816, 832, 831, 830, 821, 860,
- /* 1510 */ 859, 345, 756, 642, 755, 861, 551, 828, 637, 81,
- /* 1520 */ 820, 549, 548, 808, 829, 230, 5, 860, 859, 56,
- /* 1530 */ 311, 861, 760, 528, 862, 765, 4, 775, 862, 816,
- /* 1540 */ 829, 230, 816, 863, 806, 12, 53, 54, 754, 528,
- /* 1550 */ 548, 122, 860, 859, 55, 752, 122, 403, 18, 860,
- /* 1560 */ 859, 277, 2, 281, 280, 728, 821, 816, 122, 490,
- /* 1570 */ 862, 518, 346, 830, 859, 753, 735, 276, 316, 833,
- /* 1580 */ 727, 387, 268, 381, 750, 4, 816, 832, 831, 830,
- /* 1590 */ 860, 859, 861, 17, 630, 557, 16, 256, 344, 381,
- /* 1600 */ 860, 859, 1315, 1315, 800, 799, 821, 530, 559, 862,
- /* 1610 */ 558, 593, 861, 630, 749, 4, 553, 860, 859, 521,
- /* 1620 */ 411, 816, 494, 725, 816, 11, 806, 12, 67, 38,
- /* 1630 */ 529, 282, 284, 473, 818, 818, 65, 65, 66, 66,
- /* 1640 */ 66, 66, 821, 64, 64, 64, 64, 63, 63, 62,
- /* 1650 */ 62, 62, 61, 59, 263, 828, 115, 860, 859, 526,
- /* 1660 */ 348, 860, 859, 275, 747, 4, 862, 828, 422, 861,
- /* 1670 */ 825, 353, 495, 735, 547, 58, 593, 851, 829, 123,
- /* 1680 */ 808, 861, 828, 852, 828, 861, 56, 528, 171, 821,
- /* 1690 */ 829, 123, 862, 860, 859, 353, 861, 861, 861, 528,
- /* 1700 */ 868, 784, 547, 53, 54, 829, 230, 829, 123, 861,
- /* 1710 */ 270, 55, 748, 4, 528, 730, 528, 256, 90, 2,
- /* 1720 */ 274, 170, 347, 169, 816, 168, 635, 175, 518, 821,
- /* 1730 */ 830, 859, 860, 859, 398, 862, 833, 775, 718, 174,
- /* 1740 */ 129, 657, 402, 816, 832, 831, 830, 477, 828, 775,
- /* 1750 */ 862, 541, 92, 313, 862, 861, 392, 312, 713, 635,
- /* 1760 */ 850, 782, 861, 475, 381, 821, 775, 861, 739, 710,
- /* 1770 */ 7, 829, 123, 849, 861, 712, 862, 663, 816, 256,
- /* 1780 */ 528, 816, 861, 806, 12, 782, 68, 529, 282, 860,
- /* 1790 */ 859, 818, 818, 65, 65, 66, 66, 66, 66, 847,
+ /* 1320 */ 59, 263, 531, 1283, 333, 861, 860, 730, 450, 116,
+ /* 1330 */ 861, 860, 648, 116, 522, 678, 762, 495, 67, 68,
+ /* 1340 */ 530, 283, 649, 826, 819, 819, 65, 65, 66, 66,
+ /* 1350 */ 66, 66, 135, 64, 64, 64, 64, 63, 63, 62,
+ /* 1360 */ 62, 62, 61, 59, 263, 829, 663, 662, 531, 487,
+ /* 1370 */ 867, 861, 860, 510, 527, 535, 52, 329, 50, 862,
+ /* 1380 */ 522, 409, 540, 495, 667, 829, 634, 494, 830, 230,
+ /* 1390 */ 863, 862, 740, 354, 79, 809, 862, 529, 829, 862,
+ /* 1400 */ 761, 56, 740, 6, 863, 601, 862, 862, 830, 230,
+ /* 1410 */ 602, 122, 862, 871, 486, 81, 862, 529, 53, 54,
+ /* 1420 */ 527, 830, 123, 571, 80, 408, 55, 284, 5, 863,
+ /* 1430 */ 529, 439, 271, 494, 2, 438, 173, 22, 423, 817,
+ /* 1440 */ 756, 809, 411, 519, 518, 831, 860, 56, 382, 862,
+ /* 1450 */ 531, 834, 570, 863, 569, 829, 442, 568, 817, 833,
+ /* 1460 */ 832, 831, 522, 403, 53, 54, 22, 863, 511, 862,
+ /* 1470 */ 175, 352, 55, 396, 430, 863, 755, 863, 830, 230,
+ /* 1480 */ 2, 776, 122, 538, 783, 817, 829, 529, 863, 519,
+ /* 1490 */ 863, 831, 860, 817, 863, 514, 817, 834, 807, 12,
+ /* 1500 */ 862, 358, 527, 351, 817, 833, 832, 831, 752, 830,
+ /* 1510 */ 123, 829, 266, 861, 860, 484, 485, 643, 529, 81,
+ /* 1520 */ 115, 546, 869, 809, 753, 862, 500, 861, 860, 56,
+ /* 1530 */ 752, 18, 987, 122, 830, 123, 752, 646, 382, 817,
+ /* 1540 */ 546, 863, 817, 529, 807, 12, 53, 54, 17, 614,
+ /* 1550 */ 863, 437, 861, 860, 55, 122, 173, 691, 174, 690,
+ /* 1560 */ 852, 741, 2, 282, 281, 552, 16, 817, 546, 776,
+ /* 1570 */ 863, 519, 11, 831, 860, 58, 861, 860, 863, 834,
+ /* 1580 */ 521, 804, 803, 393, 171, 638, 817, 833, 832, 831,
+ /* 1590 */ 861, 860, 594, 552, 776, 558, 81, 863, 861, 860,
+ /* 1600 */ 861, 860, 1319, 1319, 801, 800, 76, 531, 560, 731,
+ /* 1610 */ 559, 861, 860, 861, 860, 870, 3, 861, 860, 522,
+ /* 1620 */ 180, 817, 495, 122, 817, 863, 807, 12, 67, 38,
+ /* 1630 */ 530, 283, 1255, 170, 819, 819, 65, 65, 66, 66,
+ /* 1640 */ 66, 66, 491, 64, 64, 64, 64, 63, 63, 62,
+ /* 1650 */ 62, 62, 61, 59, 263, 829, 799, 594, 549, 527,
+ /* 1660 */ 630, 784, 690, 525, 861, 860, 863, 326, 829, 862,
+ /* 1670 */ 843, 327, 496, 861, 860, 829, 550, 549, 830, 230,
+ /* 1680 */ 809, 862, 862, 285, 474, 310, 56, 529, 719, 862,
+ /* 1690 */ 44, 830, 123, 861, 860, 555, 740, 863, 830, 230,
+ /* 1700 */ 529, 861, 860, 53, 54, 549, 548, 529, 740, 112,
+ /* 1710 */ 862, 55, 305, 591, 169, 484, 475, 44, 374, 2,
+ /* 1720 */ 861, 860, 862, 168, 817, 736, 312, 354, 519, 129,
+ /* 1730 */ 831, 860, 435, 829, 548, 489, 834, 173, 382, 829,
+ /* 1740 */ 391, 862, 636, 817, 833, 832, 831, 862, 861, 860,
+ /* 1750 */ 863, 776, 863, 862, 766, 4, 830, 215, 382, 751,
+ /* 1760 */ 4, 555, 830, 211, 122, 529, 398, 395, 626, 750,
+ /* 1770 */ 4, 529, 727, 863, 467, 636, 863, 478, 817, 267,
+ /* 1780 */ 714, 817, 778, 807, 12, 740, 68, 530, 283, 861,
+ /* 1790 */ 860, 819, 819, 65, 65, 66, 66, 66, 66, 862,
/* 1800 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 1810 */ 59, 263, 530, 15, 465, 860, 859, 706, 705, 81,
- /* 1820 */ 390, 862, 121, 701, 521, 120, 273, 529, 282, 862,
- /* 1830 */ 775, 818, 818, 65, 65, 66, 66, 66, 66, 396,
+ /* 1810 */ 59, 263, 531, 736, 575, 7, 776, 713, 783, 81,
+ /* 1820 */ 861, 860, 776, 736, 522, 321, 707, 530, 283, 270,
+ /* 1830 */ 476, 819, 819, 65, 65, 66, 66, 66, 66, 862,
/* 1840 */ 64, 64, 64, 64, 63, 63, 62, 62, 62, 61,
- /* 1850 */ 59, 263, 828, 138, 862, 848, 828, 862, 860, 859,
- /* 1860 */ 37, 25, 72, 1052, 526, 669, 861, 723, 741, 861,
- /* 1870 */ 861, 545, 862, 860, 859, 829, 230, 860, 859, 829,
- /* 1880 */ 201, 845, 861, 353, 528, 808, 724, 458, 528, 862,
- /* 1890 */ 545, 56, 660, 571, 36, 861, 862, 861, 455, 860,
- /* 1900 */ 859, 723, 1315, 1315, 86, 739, 862, 333, 53, 54,
- /* 1910 */ 524, 85, 488, 24, 530, 450, 55, 323, 545, 861,
- /* 1920 */ 84, 862, 397, 828, 2, 678, 521, 714, 300, 816,
- /* 1930 */ 161, 861, 583, 518, 381, 830, 859, 861, 775, 446,
- /* 1940 */ 828, 833, 861, 739, 860, 859, 829, 211, 816, 832,
- /* 1950 */ 831, 830, 860, 859, 861, 528, 339, 861, 638, 193,
- /* 1960 */ 157, 571, 10, 829, 233, 815, 526, 105, 838, 745,
- /* 1970 */ 862, 624, 528, 782, 574, 862, 395, 860, 859, 35,
- /* 1980 */ 860, 859, 861, 816, 103, 828, 816, 808, 806, 12,
- /* 1990 */ 624, 844, 814, 56, 34, 860, 859, 33, 862, 861,
- /* 2000 */ 815, 828, 32, 102, 391, 775, 577, 393, 829, 231,
- /* 2010 */ 53, 54, 860, 859, 394, 861, 530, 528, 55, 860,
- /* 2020 */ 859, 574, 775, 616, 829, 241, 2, 330, 521, 860,
- /* 2030 */ 859, 816, 828, 528, 828, 518, 101, 830, 859, 862,
- /* 2040 */ 577, 618, 616, 833, 860, 859, 861, 828, 861, 828,
- /* 2050 */ 816, 832, 831, 830, 862, 829, 240, 829, 242, 862,
- /* 2060 */ 731, 861, 862, 861, 528, 308, 528, 775, 526, 612,
- /* 2070 */ 829, 243, 829, 262, 607, 605, 862, 426, 828, 528,
- /* 2080 */ 736, 528, 298, 775, 110, 816, 579, 581, 816, 808,
- /* 2090 */ 806, 12, 861, 860, 859, 56, 861, 826, 860, 859,
- /* 2100 */ 173, 829, 356, 296, 599, 306, 581, 575, 152, 739,
- /* 2110 */ 528, 861, 53, 54, 775, 538, 775, 861, 530, 13,
- /* 2120 */ 55, 860, 859, 861, 303, 862, 187, 828, 2, 775,
- /* 2130 */ 521, 775, 580, 816, 538, 439, 198, 518, 556, 830,
- /* 2140 */ 859, 861, 828, 96, 828, 833, 740, 555, 410, 861,
- /* 2150 */ 829, 239, 816, 832, 831, 830, 861, 862, 861, 528,
- /* 2160 */ 775, 862, 860, 859, 862, 829, 355, 829, 210, 144,
- /* 2170 */ 526, 536, 94, 256, 528, 666, 528, 860, 859, 862,
- /* 2180 */ 424, 248, 860, 859, 862, 860, 859, 816, 76, 828,
- /* 2190 */ 816, 808, 806, 12, 1205, 604, 813, 56, 252, 860,
- /* 2200 */ 859, 272, 862, 861, 828, 862, 114, 675, 385, 775,
- /* 2210 */ 861, 185, 829, 228, 53, 54, 384, 865, 861, 294,
- /* 2220 */ 530, 528, 55, 572, 775, 855, 775, 829, 232, 828,
- /* 2230 */ 2, 1207, 521, 861, 854, 816, 528, 853, 634, 518,
- /* 2240 */ 533, 830, 859, 861, 862, 184, 287, 833, 860, 859,
- /* 2250 */ 383, 828, 829, 379, 816, 832, 831, 830, 862, 653,
- /* 2260 */ 861, 528, 862, 523, 862, 861, 862, 182, 108, 447,
- /* 2270 */ 532, 775, 526, 641, 829, 378, 737, 861, 75, 359,
- /* 2280 */ 860, 859, 828, 528, 860, 859, 775, 860, 859, 816,
- /* 2290 */ 861, 862, 816, 808, 806, 12, 861, 646, 178, 56,
- /* 2300 */ 632, 824, 860, 859, 284, 829, 377, 860, 859, 358,
- /* 2310 */ 823, 775, 862, 732, 528, 628, 53, 54, 23, 489,
- /* 2320 */ 623, 591, 530, 192, 55, 860, 859, 861, 860, 859,
- /* 2330 */ 43, 828, 2, 775, 521, 822, 70, 816, 166, 305,
- /* 2340 */ 263, 518, 352, 830, 859, 861, 828, 88, 862, 833,
- /* 2350 */ 862, 279, 861, 861, 829, 227, 816, 832, 831, 830,
- /* 2360 */ 861, 480, 862, 528, 775, 700, 260, 860, 859, 829,
- /* 2370 */ 213, 405, 278, 349, 526, 861, 49, 505, 528, 861,
- /* 2380 */ 1209, 860, 859, 514, 596, 860, 859, 860, 859, 860,
- /* 2390 */ 859, 816, 335, 828, 816, 808, 806, 12, 828, 773,
- /* 2400 */ 594, 56, 1209, 772, 253, 404, 861, 861, 1209, 578,
- /* 2410 */ 769, 763, 861, 775, 860, 859, 829, 226, 53, 54,
- /* 2420 */ 862, 829, 225, 862, 676, 528, 55, 582, 775, 573,
- /* 2430 */ 528, 139, 862, 828, 2, 860, 859, 757, 861, 816,
- /* 2440 */ 140, 476, 473, 518, 702, 860, 859, 861, 165, 564,
- /* 2450 */ 862, 833, 691, 686, 1209, 654, 829, 212, 816, 832,
- /* 2460 */ 831, 830, 1209, 400, 463, 528, 542, 1209, 329, 861,
- /* 2470 */ 685, 860, 859, 860, 859, 775, 576, 322, 828, 337,
- /* 2480 */ 775, 420, 861, 681, 544, 860, 859, 682, 659, 680,
- /* 2490 */ 1209, 861, 861, 816, 543, 861, 816, 828, 806, 12,
- /* 2500 */ 375, 829, 238, 1209, 362, 1209, 1209, 652, 861, 828,
- /* 2510 */ 528, 861, 651, 374, 1209, 775, 1209, 1209, 861, 1209,
- /* 2520 */ 829, 237, 160, 861, 650, 527, 828, 649, 302, 528,
- /* 2530 */ 106, 445, 829, 209, 30, 640, 777, 1209, 828, 861,
- /* 2540 */ 861, 528, 861, 860, 859, 828, 860, 859, 159, 829,
- /* 2550 */ 124, 158, 861, 292, 137, 860, 859, 288, 528, 861,
- /* 2560 */ 775, 829, 208, 427, 828, 258, 289, 861, 829, 206,
- /* 2570 */ 528, 861, 656, 860, 859, 31, 321, 528, 861, 775,
- /* 2580 */ 861, 443, 156, 318, 199, 631, 104, 829, 234, 136,
- /* 2590 */ 155, 775, 627, 314, 783, 154, 528, 191, 828, 111,
- /* 2600 */ 828, 310, 828, 738, 434, 828, 621, 617, 775, 433,
- /* 2610 */ 615, 134, 861, 153, 861, 421, 861, 828, 133, 861,
- /* 2620 */ 775, 829, 236, 829, 229, 829, 235, 775, 829, 224,
- /* 2630 */ 528, 861, 528, 595, 528, 151, 418, 528, 828, 100,
- /* 2640 */ 829, 221, 416, 828, 150, 99, 775, 149, 98, 528,
- /* 2650 */ 148, 97, 861, 147, 30, 565, 388, 861, 146, 29,
- /* 2660 */ 552, 829, 205, 550, 131, 828, 829, 204, 546, 828,
- /* 2670 */ 528, 828, 26, 130, 145, 528, 83, 540, 186, 861,
- /* 2680 */ 775, 200, 775, 861, 775, 861, 360, 775, 829, 203,
- /* 2690 */ 786, 801, 829, 202, 829, 214, 511, 528, 189, 775,
- /* 2700 */ 828, 528, 188, 528, 60, 828, 797, 828, 743, 733,
- /* 2710 */ 338, 677, 244, 315, 861, 454, 319, 440, 370, 861,
- /* 2720 */ 775, 861, 620, 829, 219, 775, 819, 9, 829, 218,
- /* 2730 */ 829, 125, 528, 796, 785, 41, 828, 528, 664, 528,
- /* 2740 */ 444, 828, 361, 257, 525, 762, 674, 775, 668, 95,
- /* 2750 */ 861, 775, 695, 775, 655, 861, 828, 667, 694, 829,
- /* 2760 */ 217, 589, 828, 81, 829, 216, 862, 1359, 528, 1359,
- /* 2770 */ 861, 1359, 1359, 528, 1359, 1359, 861, 1359, 1359, 829,
- /* 2780 */ 222, 828, 775, 828, 1359, 829, 220, 775, 528, 775,
- /* 2790 */ 1359, 1359, 1359, 1359, 528, 861, 1359, 861, 1359, 1359,
- /* 2800 */ 1359, 1359, 1359, 1359, 829, 207, 829, 93, 1359, 1359,
- /* 2810 */ 1359, 1359, 1359, 528, 1359, 479, 1359, 1359, 775, 1359,
- /* 2820 */ 1359, 1359, 1359, 775, 1359, 1359, 1359, 1359, 1359, 1359,
- /* 2830 */ 1359, 1359, 1359, 1359, 1359, 1359, 1359, 1359, 775, 1359,
- /* 2840 */ 1359, 1359, 1359, 1359, 775, 1359, 1359, 1359, 1359, 1359,
- /* 2850 */ 1359, 1359, 1359, 1359, 1359, 1359, 1359, 1359, 1359, 1359,
- /* 2860 */ 1359, 1359, 1359, 775, 1359, 775,
+ /* 1850 */ 59, 263, 863, 346, 757, 829, 424, 829, 863, 850,
+ /* 1860 */ 726, 575, 72, 1053, 527, 15, 711, 724, 354, 862,
+ /* 1870 */ 275, 862, 863, 861, 860, 861, 860, 706, 830, 230,
+ /* 1880 */ 830, 230, 862, 121, 863, 809, 725, 529, 165, 529,
+ /* 1890 */ 572, 56, 702, 631, 748, 4, 861, 860, 37, 861,
+ /* 1900 */ 860, 724, 1319, 1319, 865, 853, 87, 397, 53, 54,
+ /* 1910 */ 749, 4, 631, 851, 531, 278, 55, 277, 862, 862,
+ /* 1920 */ 829, 863, 466, 829, 2, 679, 522, 862, 120, 817,
+ /* 1930 */ 138, 849, 274, 519, 862, 831, 860, 862, 382, 829,
+ /* 1940 */ 382, 834, 863, 830, 230, 862, 830, 233, 817, 833,
+ /* 1950 */ 832, 831, 529, 862, 256, 529, 715, 25, 572, 783,
+ /* 1960 */ 317, 670, 830, 231, 269, 459, 527, 36, 778, 661,
+ /* 1970 */ 846, 529, 456, 554, 862, 861, 860, 86, 85, 848,
+ /* 1980 */ 402, 861, 860, 817, 862, 839, 817, 809, 807, 12,
+ /* 1990 */ 827, 829, 24, 56, 816, 861, 860, 451, 863, 862,
+ /* 2000 */ 863, 625, 334, 382, 862, 862, 776, 861, 860, 84,
+ /* 2010 */ 53, 54, 863, 447, 830, 241, 531, 340, 55, 863,
+ /* 2020 */ 625, 161, 776, 529, 639, 814, 2, 331, 522, 816,
+ /* 2030 */ 10, 817, 829, 524, 193, 519, 157, 831, 860, 862,
+ /* 2040 */ 746, 105, 863, 834, 861, 860, 862, 862, 829, 863,
+ /* 2050 */ 817, 833, 832, 831, 863, 830, 240, 647, 103, 578,
+ /* 2060 */ 35, 742, 862, 34, 529, 861, 860, 738, 527, 33,
+ /* 2070 */ 32, 830, 242, 829, 776, 862, 1202, 863, 829, 102,
+ /* 2080 */ 529, 862, 863, 394, 829, 817, 392, 862, 817, 809,
+ /* 2090 */ 807, 12, 862, 578, 101, 56, 830, 243, 862, 309,
+ /* 2100 */ 314, 830, 262, 733, 313, 529, 619, 830, 357, 426,
+ /* 2110 */ 529, 613, 53, 54, 862, 776, 529, 862, 531, 608,
+ /* 2120 */ 55, 861, 860, 861, 860, 863, 606, 829, 2, 617,
+ /* 2130 */ 522, 776, 110, 817, 654, 861, 860, 519, 173, 831,
+ /* 2140 */ 860, 862, 861, 860, 600, 834, 166, 863, 617, 481,
+ /* 2150 */ 830, 239, 817, 833, 832, 831, 776, 829, 642, 529,
+ /* 2160 */ 862, 776, 732, 862, 676, 861, 860, 776, 701, 307,
+ /* 2170 */ 527, 862, 861, 860, 336, 152, 13, 861, 860, 187,
+ /* 2180 */ 830, 356, 862, 304, 829, 198, 581, 817, 862, 529,
+ /* 2190 */ 817, 809, 807, 12, 1209, 829, 144, 56, 862, 637,
+ /* 2200 */ 861, 860, 863, 677, 863, 861, 860, 830, 210, 862,
+ /* 2210 */ 776, 557, 655, 605, 53, 54, 529, 862, 830, 228,
+ /* 2220 */ 531, 96, 55, 863, 556, 410, 862, 529, 863, 537,
+ /* 2230 */ 2, 1211, 522, 252, 94, 817, 829, 330, 635, 519,
+ /* 2240 */ 776, 831, 860, 863, 256, 863, 248, 834, 861, 860,
+ /* 2250 */ 862, 862, 829, 863, 817, 833, 832, 831, 273, 830,
+ /* 2260 */ 232, 633, 386, 114, 597, 863, 862, 776, 529, 866,
+ /* 2270 */ 861, 860, 527, 185, 385, 830, 380, 829, 776, 856,
+ /* 2280 */ 184, 108, 829, 629, 529, 854, 182, 863, 829, 817,
+ /* 2290 */ 855, 862, 817, 809, 807, 12, 862, 534, 533, 56,
+ /* 2300 */ 830, 379, 862, 448, 863, 830, 378, 323, 75, 529,
+ /* 2310 */ 178, 830, 227, 825, 529, 285, 53, 54, 23, 776,
+ /* 2320 */ 529, 862, 531, 824, 55, 861, 860, 861, 860, 863,
+ /* 2330 */ 490, 829, 2, 43, 522, 776, 70, 817, 624, 592,
+ /* 2340 */ 595, 519, 263, 831, 860, 862, 861, 860, 863, 834,
+ /* 2350 */ 863, 861, 860, 360, 830, 213, 817, 833, 832, 831,
+ /* 2360 */ 776, 829, 582, 529, 583, 776, 861, 860, 861, 860,
+ /* 2370 */ 359, 776, 420, 353, 527, 862, 861, 860, 544, 192,
+ /* 2380 */ 1213, 582, 280, 823, 830, 226, 862, 88, 861, 860,
+ /* 2390 */ 405, 817, 862, 529, 817, 809, 807, 12, 829, 301,
+ /* 2400 */ 260, 56, 1213, 584, 539, 515, 363, 577, 1213, 279,
+ /* 2410 */ 861, 860, 862, 862, 776, 49, 579, 528, 53, 54,
+ /* 2420 */ 862, 830, 225, 539, 829, 350, 55, 861, 860, 863,
+ /* 2430 */ 529, 862, 863, 506, 2, 324, 565, 773, 862, 817,
+ /* 2440 */ 774, 440, 404, 519, 776, 861, 860, 830, 212, 862,
+ /* 2450 */ 770, 834, 861, 860, 1213, 862, 529, 764, 817, 833,
+ /* 2460 */ 832, 831, 1213, 829, 543, 545, 758, 1213, 306, 303,
+ /* 2470 */ 253, 861, 860, 861, 860, 139, 140, 862, 474, 477,
+ /* 2480 */ 299, 776, 862, 862, 580, 165, 830, 238, 829, 574,
+ /* 2490 */ 1213, 692, 464, 817, 862, 529, 817, 703, 807, 12,
+ /* 2500 */ 686, 687, 862, 1213, 829, 1213, 1213, 776, 293, 829,
+ /* 2510 */ 289, 830, 237, 400, 1213, 829, 1213, 1213, 862, 1213,
+ /* 2520 */ 529, 739, 862, 862, 862, 338, 829, 830, 209, 862,
+ /* 2530 */ 297, 682, 830, 124, 576, 376, 529, 1213, 830, 208,
+ /* 2540 */ 862, 529, 681, 290, 862, 829, 776, 529, 660, 830,
+ /* 2550 */ 206, 375, 861, 860, 657, 861, 860, 862, 529, 862,
+ /* 2560 */ 295, 829, 288, 683, 573, 829, 384, 829, 830, 234,
+ /* 2570 */ 641, 776, 160, 106, 862, 862, 862, 529, 653, 862,
+ /* 2580 */ 652, 862, 651, 650, 830, 236, 159, 776, 830, 229,
+ /* 2590 */ 830, 235, 776, 529, 446, 137, 258, 529, 776, 529,
+ /* 2600 */ 829, 30, 829, 158, 322, 427, 829, 156, 31, 776,
+ /* 2610 */ 444, 199, 632, 104, 862, 136, 862, 319, 155, 628,
+ /* 2620 */ 862, 154, 829, 830, 224, 830, 221, 315, 776, 830,
+ /* 2630 */ 205, 111, 529, 311, 529, 434, 862, 433, 529, 622,
+ /* 2640 */ 616, 134, 829, 618, 776, 830, 204, 829, 776, 829,
+ /* 2650 */ 776, 421, 191, 133, 529, 153, 862, 596, 418, 151,
+ /* 2660 */ 100, 862, 416, 862, 829, 830, 203, 150, 99, 149,
+ /* 2670 */ 830, 202, 830, 214, 529, 148, 98, 97, 862, 529,
+ /* 2680 */ 147, 529, 30, 776, 566, 776, 389, 830, 219, 776,
+ /* 2690 */ 829, 553, 829, 146, 829, 29, 529, 829, 26, 551,
+ /* 2700 */ 131, 130, 145, 547, 862, 776, 862, 541, 862, 83,
+ /* 2710 */ 200, 862, 186, 830, 218, 830, 125, 830, 217, 829,
+ /* 2720 */ 830, 216, 529, 60, 529, 776, 529, 361, 189, 529,
+ /* 2730 */ 776, 829, 776, 862, 787, 188, 829, 744, 802, 798,
+ /* 2740 */ 512, 339, 830, 222, 678, 862, 734, 776, 455, 244,
+ /* 2750 */ 862, 529, 320, 441, 830, 220, 316, 623, 621, 830,
+ /* 2760 */ 207, 371, 829, 529, 9, 820, 797, 526, 529, 257,
+ /* 2770 */ 786, 665, 362, 776, 41, 776, 862, 776, 445, 763,
+ /* 2780 */ 776, 95, 675, 696, 695, 830, 93, 590, 81, 863,
+ /* 2790 */ 669, 668, 1363, 1363, 480, 1363, 656, 1363, 1363, 1363,
+ /* 2800 */ 1363, 1363, 776, 1363, 1363, 1363, 1363, 1363, 1363, 1363,
+ /* 2810 */ 1363, 1363, 1363, 1363, 776, 1363, 1363, 1363, 1363, 776,
+ /* 2820 */ 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363,
+ /* 2830 */ 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363, 1363,
+ /* 2840 */ 1363, 1363, 1363, 1363, 1363, 776,
};
static const YYCODETYPE yy_lookahead[] = {
- /* 0 */ 4, 131, 24, 31, 134, 135, 136, 50, 81, 82,
- /* 10 */ 83, 84, 16, 41, 87, 88, 89, 90, 91, 92,
- /* 20 */ 93, 94, 152, 96, 97, 98, 99, 100, 101, 102,
+ /* 0 */ 4, 102, 103, 104, 105, 106, 107, 50, 81, 82,
+ /* 10 */ 83, 84, 16, 217, 87, 88, 89, 90, 91, 92,
+ /* 20 */ 93, 94, 226, 96, 97, 98, 99, 100, 101, 102,
/* 30 */ 103, 104, 105, 106, 107, 102, 109, 117, 81, 82,
/* 40 */ 83, 84, 122, 122, 87, 88, 89, 90, 91, 92,
/* 50 */ 93, 94, 56, 96, 97, 98, 99, 100, 101, 102,
- /* 60 */ 103, 104, 105, 106, 107, 144, 109, 102, 103, 104,
- /* 70 */ 105, 106, 107, 77, 148, 91, 92, 93, 94, 83,
+ /* 60 */ 103, 104, 105, 106, 107, 215, 109, 100, 101, 219,
+ /* 70 */ 220, 221, 116, 77, 118, 91, 92, 93, 94, 83,
/* 80 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 90 */ 106, 107, 159, 4, 116, 162, 100, 101, 102, 42,
- /* 100 */ 43, 203, 203, 177, 108, 109, 83, 211, 68, 44,
- /* 110 */ 4, 71, 116, 117, 122, 217, 217, 121, 122, 203,
- /* 120 */ 109, 125, 16, 127, 128, 226, 227, 132, 133, 133,
- /* 130 */ 24, 4, 68, 217, 235, 71, 140, 141, 142, 143,
- /* 140 */ 242, 145, 85, 86, 248, 249, 4, 9, 83, 11,
- /* 150 */ 158, 13, 160, 161, 158, 115, 160, 161, 203, 80,
- /* 160 */ 164, 23, 56, 113, 26, 169, 170, 171, 172, 173,
- /* 170 */ 174, 175, 217, 277, 178, 279, 180, 181, 282, 115,
- /* 180 */ 203, 226, 227, 77, 285, 162, 43, 288, 192, 83,
- /* 190 */ 235, 293, 54, 117, 217, 116, 117, 59, 302, 303,
- /* 200 */ 223, 224, 64, 65, 117, 116, 100, 101, 70, 122,
- /* 210 */ 121, 73, 19, 75, 108, 109, 127, 128, 263, 264,
- /* 220 */ 4, 203, 116, 117, 4, 185, 83, 121, 122, 140,
- /* 230 */ 314, 125, 16, 127, 128, 217, 122, 5, 45, 133,
- /* 240 */ 285, 223, 224, 116, 155, 118, 140, 141, 142, 143,
- /* 250 */ 112, 145, 114, 122, 127, 166, 167, 203, 116, 182,
- /* 260 */ 67, 184, 30, 121, 158, 203, 160, 161, 36, 127,
- /* 270 */ 128, 217, 56, 296, 297, 169, 170, 171, 172, 217,
- /* 280 */ 174, 175, 140, 116, 178, 118, 180, 181, 145, 4,
- /* 290 */ 163, 153, 60, 77, 151, 164, 64, 155, 192, 83,
+ /* 90 */ 106, 107, 159, 4, 173, 162, 100, 101, 102, 60,
+ /* 100 */ 127, 219, 220, 221, 108, 109, 133, 211, 141, 142,
+ /* 110 */ 4, 203, 116, 117, 141, 142, 143, 121, 122, 225,
+ /* 120 */ 35, 125, 16, 127, 128, 217, 203, 233, 234, 133,
+ /* 130 */ 24, 146, 147, 148, 226, 227, 140, 141, 142, 143,
+ /* 140 */ 217, 145, 57, 235, 248, 249, 4, 9, 63, 11,
+ /* 150 */ 4, 13, 109, 76, 158, 148, 160, 161, 203, 113,
+ /* 160 */ 164, 23, 56, 43, 26, 169, 170, 171, 172, 173,
+ /* 170 */ 174, 175, 217, 277, 178, 279, 180, 181, 282, 203,
+ /* 180 */ 117, 226, 227, 77, 177, 146, 147, 148, 192, 83,
+ /* 190 */ 235, 4, 54, 217, 286, 156, 157, 59, 68, 303,
+ /* 200 */ 304, 71, 64, 65, 117, 116, 100, 101, 70, 122,
+ /* 210 */ 121, 73, 5, 75, 108, 109, 127, 128, 263, 264,
+ /* 220 */ 4, 131, 116, 117, 134, 135, 136, 121, 122, 140,
+ /* 230 */ 153, 125, 16, 127, 128, 133, 313, 30, 315, 133,
+ /* 240 */ 203, 286, 152, 36, 155, 115, 140, 141, 142, 143,
+ /* 250 */ 112, 145, 114, 151, 217, 166, 167, 122, 116, 90,
+ /* 260 */ 223, 224, 116, 121, 158, 145, 160, 161, 191, 127,
+ /* 270 */ 128, 64, 56, 127, 128, 169, 170, 171, 172, 144,
+ /* 280 */ 174, 175, 140, 15, 178, 116, 180, 181, 222, 223,
+ /* 290 */ 224, 153, 4, 77, 318, 319, 320, 155, 192, 83,
/* 300 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 310 */ 106, 107, 35, 21, 296, 297, 100, 101, 117, 60,
- /* 320 */ 28, 122, 203, 122, 108, 109, 117, 128, 190, 37,
- /* 330 */ 211, 122, 116, 117, 57, 145, 217, 121, 122, 5,
- /* 340 */ 63, 125, 4, 127, 128, 226, 227, 127, 128, 133,
- /* 350 */ 196, 197, 198, 199, 235, 165, 140, 141, 142, 143,
- /* 360 */ 140, 145, 117, 170, 30, 166, 167, 122, 249, 169,
- /* 370 */ 36, 317, 318, 319, 158, 133, 160, 161, 316, 203,
- /* 380 */ 42, 43, 263, 264, 7, 169, 203, 171, 172, 12,
- /* 390 */ 174, 175, 192, 217, 178, 175, 180, 181, 64, 122,
- /* 400 */ 217, 116, 226, 227, 285, 146, 147, 148, 192, 226,
- /* 410 */ 227, 235, 127, 128, 26, 156, 157, 40, 235, 81,
+ /* 310 */ 106, 107, 122, 45, 127, 128, 100, 101, 105, 106,
+ /* 320 */ 107, 175, 203, 122, 108, 109, 203, 140, 190, 61,
+ /* 330 */ 211, 116, 116, 117, 297, 298, 217, 121, 122, 4,
+ /* 340 */ 217, 125, 4, 127, 128, 226, 227, 19, 158, 133,
+ /* 350 */ 160, 161, 133, 203, 235, 203, 140, 141, 142, 143,
+ /* 360 */ 208, 145, 175, 21, 298, 213, 214, 217, 249, 217,
+ /* 370 */ 28, 132, 133, 45, 158, 203, 160, 161, 203, 37,
+ /* 380 */ 42, 43, 263, 264, 119, 169, 203, 171, 172, 217,
+ /* 390 */ 174, 175, 217, 31, 178, 67, 180, 181, 226, 227,
+ /* 400 */ 217, 226, 227, 41, 116, 286, 119, 235, 192, 121,
+ /* 410 */ 235, 42, 43, 4, 26, 127, 128, 294, 150, 81,
/* 420 */ 82, 83, 84, 85, 86, 87, 88, 89, 90, 91,
- /* 430 */ 92, 93, 94, 90, 96, 97, 98, 99, 100, 101,
+ /* 430 */ 92, 93, 94, 4, 96, 97, 98, 99, 100, 101,
/* 440 */ 102, 103, 104, 105, 106, 107, 100, 101, 102, 103,
- /* 450 */ 104, 105, 106, 107, 141, 142, 118, 117, 275, 116,
- /* 460 */ 175, 285, 122, 42, 43, 127, 308, 309, 285, 81,
- /* 470 */ 82, 83, 84, 52, 116, 87, 88, 89, 90, 91,
- /* 480 */ 92, 93, 94, 76, 96, 97, 98, 99, 100, 101,
- /* 490 */ 102, 103, 104, 105, 106, 107, 320, 122, 119, 323,
- /* 500 */ 80, 163, 81, 82, 83, 84, 85, 86, 87, 88,
- /* 510 */ 89, 90, 91, 92, 93, 94, 4, 96, 97, 98,
+ /* 450 */ 104, 105, 106, 107, 85, 86, 118, 43, 286, 24,
+ /* 460 */ 169, 286, 127, 42, 43, 127, 316, 317, 116, 81,
+ /* 470 */ 82, 83, 84, 52, 139, 87, 88, 89, 90, 91,
+ /* 480 */ 92, 93, 94, 192, 96, 97, 98, 99, 100, 101,
+ /* 490 */ 102, 103, 104, 105, 106, 107, 321, 83, 170, 324,
+ /* 500 */ 317, 163, 81, 82, 83, 84, 85, 86, 87, 88,
+ /* 510 */ 89, 90, 91, 92, 93, 94, 80, 96, 97, 98,
/* 520 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 10,
- /* 530 */ 117, 291, 203, 127, 133, 122, 116, 117, 119, 133,
- /* 540 */ 203, 22, 122, 122, 169, 208, 217, 141, 142, 143,
- /* 550 */ 213, 214, 151, 116, 217, 226, 227, 222, 223, 224,
- /* 560 */ 153, 42, 43, 215, 235, 325, 326, 219, 220, 221,
- /* 570 */ 182, 73, 184, 91, 92, 93, 94, 95, 96, 97,
+ /* 530 */ 203, 80, 44, 4, 203, 5, 127, 128, 146, 147,
+ /* 540 */ 148, 22, 122, 122, 217, 116, 116, 118, 217, 140,
+ /* 550 */ 205, 116, 116, 117, 223, 224, 127, 4, 122, 145,
+ /* 560 */ 30, 42, 43, 73, 155, 151, 36, 116, 117, 117,
+ /* 570 */ 182, 83, 184, 91, 92, 93, 94, 95, 96, 97,
/* 580 */ 98, 99, 100, 101, 102, 103, 104, 105, 106, 107,
- /* 590 */ 217, 4, 263, 264, 100, 101, 4, 26, 191, 226,
+ /* 590 */ 60, 4, 163, 68, 64, 268, 71, 26, 80, 109,
/* 600 */ 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
- /* 610 */ 91, 92, 93, 94, 285, 96, 97, 98, 99, 100,
- /* 620 */ 101, 102, 103, 104, 105, 106, 107, 4, 116, 35,
- /* 630 */ 132, 203, 297, 121, 117, 141, 142, 10, 233, 127,
- /* 640 */ 128, 236, 203, 42, 43, 217, 207, 53, 243, 22,
- /* 650 */ 58, 57, 81, 82, 83, 84, 217, 63, 87, 88,
- /* 660 */ 89, 90, 91, 92, 93, 94, 4, 96, 97, 98,
- /* 670 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 146,
- /* 680 */ 147, 148, 81, 82, 83, 84, 85, 86, 87, 88,
- /* 690 */ 89, 90, 91, 92, 93, 94, 122, 96, 97, 98,
+ /* 610 */ 91, 92, 93, 94, 35, 96, 97, 98, 99, 100,
+ /* 620 */ 101, 102, 103, 104, 105, 106, 107, 203, 297, 298,
+ /* 630 */ 21, 203, 53, 4, 116, 117, 57, 203, 293, 4,
+ /* 640 */ 115, 217, 63, 42, 43, 217, 37, 213, 214, 120,
+ /* 650 */ 121, 217, 81, 82, 83, 84, 127, 128, 87, 88,
+ /* 660 */ 89, 90, 91, 92, 93, 94, 117, 96, 97, 98,
+ /* 670 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 117,
+ /* 680 */ 127, 128, 81, 82, 83, 84, 85, 86, 87, 88,
+ /* 690 */ 89, 90, 91, 92, 93, 94, 116, 96, 97, 98,
/* 700 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 32,
- /* 710 */ 203, 122, 120, 126, 127, 128, 203, 13, 131, 127,
- /* 720 */ 128, 134, 135, 136, 217, 117, 213, 214, 203, 260,
- /* 730 */ 217, 262, 55, 250, 251, 210, 253, 212, 43, 152,
- /* 740 */ 225, 21, 217, 120, 121, 317, 318, 319, 233, 234,
- /* 750 */ 127, 128, 239, 182, 241, 184, 4, 37, 81, 82,
- /* 760 */ 83, 84, 173, 169, 87, 88, 89, 90, 91, 92,
- /* 770 */ 93, 94, 38, 96, 97, 98, 99, 100, 101, 102,
- /* 780 */ 103, 104, 105, 106, 107, 81, 82, 83, 84, 127,
- /* 790 */ 128, 87, 88, 89, 90, 91, 92, 93, 94, 35,
+ /* 710 */ 185, 203, 117, 126, 127, 128, 203, 13, 131, 29,
+ /* 720 */ 212, 134, 135, 136, 203, 217, 213, 214, 175, 145,
+ /* 730 */ 217, 210, 55, 212, 196, 197, 198, 199, 217, 152,
+ /* 740 */ 122, 117, 318, 319, 320, 122, 122, 4, 169, 165,
+ /* 750 */ 121, 128, 239, 182, 241, 184, 127, 128, 81, 82,
+ /* 760 */ 83, 84, 127, 128, 87, 88, 89, 90, 91, 92,
+ /* 770 */ 93, 94, 117, 96, 97, 98, 99, 100, 101, 102,
+ /* 780 */ 103, 104, 105, 106, 107, 81, 82, 83, 84, 166,
+ /* 790 */ 167, 87, 88, 89, 90, 91, 92, 93, 94, 109,
/* 800 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 810 */ 106, 107, 4, 109, 195, 4, 154, 83, 203, 200,
- /* 820 */ 34, 57, 315, 316, 16, 203, 74, 63, 66, 79,
- /* 830 */ 211, 291, 217, 211, 72, 81, 82, 83, 84, 217,
- /* 840 */ 145, 87, 88, 89, 90, 91, 92, 93, 94, 117,
+ /* 810 */ 106, 107, 4, 109, 203, 4, 203, 188, 159, 203,
+ /* 820 */ 34, 162, 4, 66, 16, 141, 142, 211, 217, 72,
+ /* 830 */ 217, 80, 4, 217, 4, 81, 82, 83, 84, 229,
+ /* 840 */ 4, 87, 88, 89, 90, 91, 92, 93, 94, 4,
/* 850 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 860 */ 106, 107, 4, 203, 56, 325, 326, 248, 249, 83,
- /* 870 */ 203, 249, 118, 105, 106, 107, 124, 217, 80, 127,
- /* 880 */ 128, 73, 267, 268, 217, 77, 226, 227, 77, 267,
- /* 890 */ 268, 83, 122, 107, 117, 235, 277, 135, 279, 203,
- /* 900 */ 255, 282, 211, 207, 118, 222, 223, 224, 100, 101,
- /* 910 */ 265, 100, 101, 217, 116, 117, 108, 131, 132, 133,
- /* 920 */ 134, 135, 136, 137, 116, 117, 307, 116, 116, 121,
- /* 930 */ 146, 147, 148, 125, 164, 127, 128, 151, 127, 248,
- /* 940 */ 249, 133, 80, 193, 133, 285, 117, 185, 140, 141,
- /* 950 */ 142, 143, 141, 142, 143, 219, 220, 221, 116, 4,
- /* 960 */ 293, 117, 26, 203, 156, 157, 122, 244, 277, 246,
- /* 970 */ 279, 250, 251, 282, 253, 26, 118, 217, 116, 117,
- /* 980 */ 297, 203, 4, 175, 122, 127, 178, 117, 180, 181,
- /* 990 */ 81, 82, 83, 84, 303, 217, 87, 88, 89, 90,
- /* 1000 */ 91, 92, 93, 94, 283, 96, 97, 98, 99, 100,
+ /* 860 */ 106, 107, 4, 203, 56, 249, 123, 116, 117, 83,
+ /* 870 */ 127, 128, 118, 122, 229, 203, 203, 217, 267, 268,
+ /* 880 */ 117, 73, 10, 267, 268, 77, 226, 227, 77, 217,
+ /* 890 */ 217, 83, 135, 107, 22, 235, 292, 287, 226, 227,
+ /* 900 */ 250, 251, 211, 253, 118, 117, 44, 235, 100, 101,
+ /* 910 */ 122, 100, 101, 122, 219, 242, 108, 131, 132, 133,
+ /* 920 */ 134, 135, 136, 137, 116, 117, 313, 116, 315, 121,
+ /* 930 */ 326, 327, 287, 125, 116, 127, 128, 151, 127, 248,
+ /* 940 */ 249, 133, 185, 292, 133, 127, 286, 275, 140, 141,
+ /* 950 */ 142, 143, 141, 142, 143, 127, 128, 127, 286, 4,
+ /* 960 */ 169, 266, 26, 127, 156, 157, 138, 294, 277, 139,
+ /* 970 */ 279, 117, 127, 282, 129, 139, 118, 326, 327, 116,
+ /* 980 */ 203, 321, 287, 175, 324, 127, 178, 26, 180, 181,
+ /* 990 */ 81, 82, 83, 84, 217, 304, 87, 88, 89, 90,
+ /* 1000 */ 91, 92, 93, 94, 182, 96, 97, 98, 99, 100,
/* 1010 */ 101, 102, 103, 104, 105, 106, 107, 81, 82, 83,
- /* 1020 */ 84, 163, 73, 87, 88, 89, 90, 91, 92, 93,
- /* 1030 */ 94, 44, 96, 97, 98, 99, 100, 101, 102, 103,
- /* 1040 */ 104, 105, 106, 107, 81, 82, 83, 84, 217, 218,
- /* 1050 */ 87, 88, 89, 90, 91, 92, 93, 94, 109, 96,
+ /* 1020 */ 84, 163, 117, 87, 88, 89, 90, 91, 92, 93,
+ /* 1030 */ 94, 162, 96, 97, 98, 99, 100, 101, 102, 103,
+ /* 1040 */ 104, 105, 106, 107, 81, 82, 83, 84, 164, 35,
+ /* 1050 */ 87, 88, 89, 90, 91, 92, 93, 94, 203, 96,
/* 1060 */ 97, 98, 99, 100, 101, 102, 103, 104, 105, 106,
- /* 1070 */ 107, 117, 312, 295, 314, 120, 121, 0, 81, 82,
+ /* 1070 */ 107, 57, 217, 296, 164, 120, 121, 63, 81, 82,
/* 1080 */ 83, 84, 127, 128, 87, 88, 89, 90, 91, 92,
/* 1090 */ 93, 94, 183, 96, 97, 98, 99, 100, 101, 102,
- /* 1100 */ 103, 104, 105, 106, 107, 127, 29, 129, 4, 81,
+ /* 1100 */ 103, 104, 105, 106, 107, 309, 310, 83, 4, 81,
/* 1110 */ 82, 83, 84, 122, 117, 87, 88, 89, 90, 91,
/* 1120 */ 92, 93, 94, 203, 96, 97, 98, 99, 100, 101,
- /* 1130 */ 102, 103, 104, 105, 106, 107, 159, 217, 4, 162,
- /* 1140 */ 116, 81, 82, 83, 84, 117, 183, 87, 88, 89,
- /* 1150 */ 90, 91, 92, 93, 94, 26, 96, 97, 98, 99,
- /* 1160 */ 100, 101, 102, 103, 104, 105, 106, 107, 182, 198,
- /* 1170 */ 199, 117, 81, 82, 83, 84, 122, 117, 87, 88,
- /* 1180 */ 89, 90, 91, 92, 93, 94, 109, 96, 97, 98,
- /* 1190 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 117,
- /* 1200 */ 280, 4, 117, 81, 82, 83, 84, 122, 117, 87,
- /* 1210 */ 88, 89, 90, 91, 92, 93, 94, 219, 96, 97,
+ /* 1130 */ 102, 103, 104, 105, 106, 107, 122, 217, 4, 14,
+ /* 1140 */ 4, 81, 82, 83, 84, 117, 183, 87, 88, 89,
+ /* 1150 */ 90, 91, 92, 93, 94, 164, 96, 97, 98, 99,
+ /* 1160 */ 100, 101, 102, 103, 104, 105, 106, 107, 250, 251,
+ /* 1170 */ 315, 253, 81, 82, 83, 84, 122, 117, 87, 88,
+ /* 1180 */ 89, 90, 91, 92, 93, 94, 162, 96, 97, 98,
+ /* 1190 */ 99, 100, 101, 102, 103, 104, 105, 106, 107, 122,
+ /* 1200 */ 280, 283, 4, 81, 82, 83, 84, 4, 117, 87,
+ /* 1210 */ 88, 89, 90, 91, 92, 93, 94, 116, 96, 97,
/* 1220 */ 98, 99, 100, 101, 102, 103, 104, 105, 106, 107,
- /* 1230 */ 162, 127, 128, 117, 81, 82, 83, 84, 122, 117,
+ /* 1230 */ 118, 127, 128, 117, 81, 82, 83, 84, 122, 117,
/* 1240 */ 87, 88, 89, 90, 91, 92, 93, 94, 4, 96,
/* 1250 */ 97, 98, 99, 100, 101, 102, 103, 104, 105, 106,
- /* 1260 */ 107, 127, 128, 15, 266, 4, 81, 82, 83, 84,
+ /* 1260 */ 107, 127, 128, 127, 128, 117, 81, 82, 83, 84,
/* 1270 */ 166, 118, 87, 88, 89, 90, 91, 92, 93, 94,
/* 1280 */ 219, 96, 97, 98, 99, 100, 101, 102, 103, 104,
- /* 1290 */ 105, 106, 107, 45, 109, 81, 82, 83, 84, 4,
- /* 1300 */ 166, 87, 88, 89, 90, 91, 92, 93, 94, 61,
+ /* 1290 */ 105, 106, 107, 14, 109, 81, 82, 83, 84, 163,
+ /* 1300 */ 166, 87, 88, 89, 90, 91, 92, 93, 94, 111,
/* 1310 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 1320 */ 106, 107, 4, 109, 127, 128, 117, 266, 203, 203,
- /* 1330 */ 219, 122, 207, 73, 16, 138, 164, 19, 81, 82,
- /* 1340 */ 83, 84, 217, 217, 87, 88, 89, 90, 91, 92,
- /* 1350 */ 93, 94, 4, 96, 97, 98, 99, 100, 101, 102,
- /* 1360 */ 103, 104, 105, 106, 107, 121, 164, 203, 4, 109,
- /* 1370 */ 203, 127, 128, 117, 56, 211, 14, 266, 122, 211,
- /* 1380 */ 16, 217, 121, 19, 217, 4, 4, 69, 127, 128,
- /* 1390 */ 226, 227, 203, 226, 227, 77, 203, 286, 150, 235,
- /* 1400 */ 118, 83, 235, 85, 4, 212, 217, 203, 122, 117,
- /* 1410 */ 217, 116, 122, 249, 122, 226, 227, 249, 100, 101,
- /* 1420 */ 56, 217, 127, 128, 235, 116, 108, 263, 203, 4,
- /* 1430 */ 263, 264, 188, 69, 116, 35, 4, 117, 312, 121,
- /* 1440 */ 314, 77, 217, 125, 211, 127, 128, 83, 187, 285,
- /* 1450 */ 4, 133, 285, 53, 203, 203, 255, 57, 140, 141,
- /* 1460 */ 142, 143, 16, 63, 100, 101, 265, 4, 217, 217,
- /* 1470 */ 175, 244, 108, 246, 285, 127, 128, 4, 226, 227,
- /* 1480 */ 116, 203, 249, 14, 280, 121, 203, 235, 140, 125,
- /* 1490 */ 47, 127, 128, 175, 4, 217, 178, 133, 180, 181,
- /* 1500 */ 217, 203, 56, 121, 140, 141, 142, 143, 127, 127,
- /* 1510 */ 128, 322, 323, 211, 32, 217, 168, 203, 211, 73,
- /* 1520 */ 139, 139, 140, 77, 226, 227, 82, 127, 128, 83,
- /* 1530 */ 211, 217, 62, 235, 4, 318, 319, 285, 4, 175,
- /* 1540 */ 226, 227, 178, 111, 180, 181, 100, 101, 62, 235,
- /* 1550 */ 168, 249, 127, 128, 108, 55, 249, 274, 14, 127,
- /* 1560 */ 128, 263, 116, 100, 101, 140, 4, 121, 249, 169,
- /* 1570 */ 4, 125, 320, 127, 128, 323, 219, 263, 203, 133,
- /* 1580 */ 155, 205, 207, 285, 318, 319, 140, 141, 142, 143,
- /* 1590 */ 127, 128, 217, 14, 121, 132, 14, 286, 203, 285,
- /* 1600 */ 127, 128, 156, 157, 141, 142, 4, 4, 145, 4,
- /* 1610 */ 147, 121, 217, 140, 318, 319, 305, 127, 128, 16,
- /* 1620 */ 29, 175, 19, 266, 178, 14, 180, 181, 81, 82,
- /* 1630 */ 83, 84, 156, 157, 87, 88, 89, 90, 91, 92,
- /* 1640 */ 93, 94, 4, 96, 97, 98, 99, 100, 101, 102,
- /* 1650 */ 103, 104, 105, 106, 107, 203, 116, 127, 128, 56,
- /* 1660 */ 229, 127, 128, 268, 318, 319, 4, 203, 292, 217,
- /* 1670 */ 140, 203, 69, 219, 140, 122, 186, 111, 226, 227,
- /* 1680 */ 77, 217, 203, 203, 203, 217, 83, 235, 14, 127,
- /* 1690 */ 226, 227, 4, 127, 128, 203, 217, 217, 217, 235,
- /* 1700 */ 109, 139, 168, 100, 101, 226, 227, 226, 227, 217,
- /* 1710 */ 242, 108, 318, 319, 235, 38, 235, 286, 116, 116,
- /* 1720 */ 266, 117, 229, 117, 121, 117, 121, 275, 125, 127,
- /* 1730 */ 127, 128, 127, 128, 242, 4, 133, 285, 166, 275,
- /* 1740 */ 119, 203, 263, 140, 141, 142, 143, 119, 203, 285,
- /* 1750 */ 4, 213, 214, 203, 4, 217, 275, 207, 102, 154,
- /* 1760 */ 203, 293, 217, 122, 285, 127, 285, 217, 203, 159,
- /* 1770 */ 116, 226, 227, 111, 217, 117, 4, 139, 175, 286,
- /* 1780 */ 235, 178, 217, 180, 181, 293, 82, 83, 84, 127,
- /* 1790 */ 128, 87, 88, 89, 90, 91, 92, 93, 94, 111,
+ /* 1320 */ 106, 107, 4, 109, 117, 127, 128, 266, 117, 122,
+ /* 1330 */ 127, 128, 233, 122, 16, 236, 47, 19, 81, 82,
+ /* 1340 */ 83, 84, 243, 140, 87, 88, 89, 90, 91, 92,
+ /* 1350 */ 93, 94, 122, 96, 97, 98, 99, 100, 101, 102,
+ /* 1360 */ 103, 104, 105, 106, 107, 203, 217, 218, 4, 38,
+ /* 1370 */ 195, 127, 128, 211, 56, 200, 182, 203, 184, 217,
+ /* 1380 */ 16, 207, 203, 19, 140, 203, 211, 69, 226, 227,
+ /* 1390 */ 4, 217, 203, 203, 164, 77, 217, 235, 203, 217,
+ /* 1400 */ 62, 83, 203, 85, 4, 7, 217, 217, 226, 227,
+ /* 1410 */ 12, 249, 217, 0, 83, 73, 217, 235, 100, 101,
+ /* 1420 */ 56, 226, 227, 248, 249, 263, 108, 255, 82, 4,
+ /* 1430 */ 235, 117, 242, 69, 116, 203, 122, 265, 40, 121,
+ /* 1440 */ 32, 77, 29, 125, 211, 127, 128, 83, 286, 217,
+ /* 1450 */ 4, 133, 277, 4, 279, 203, 255, 282, 140, 141,
+ /* 1460 */ 142, 143, 16, 274, 100, 101, 265, 4, 286, 217,
+ /* 1470 */ 275, 289, 108, 274, 132, 4, 62, 4, 226, 227,
+ /* 1480 */ 116, 286, 249, 308, 294, 121, 203, 235, 4, 125,
+ /* 1490 */ 4, 127, 128, 175, 4, 211, 178, 133, 180, 181,
+ /* 1500 */ 217, 260, 56, 262, 140, 141, 142, 143, 35, 226,
+ /* 1510 */ 227, 203, 280, 127, 128, 263, 264, 211, 235, 73,
+ /* 1520 */ 116, 121, 109, 77, 55, 217, 53, 127, 128, 83,
+ /* 1530 */ 57, 14, 117, 249, 226, 227, 63, 122, 286, 175,
+ /* 1540 */ 140, 4, 178, 235, 180, 181, 100, 101, 14, 26,
+ /* 1550 */ 4, 117, 127, 128, 108, 249, 122, 244, 275, 246,
+ /* 1560 */ 111, 175, 116, 100, 101, 140, 14, 121, 168, 286,
+ /* 1570 */ 4, 125, 14, 127, 128, 122, 127, 128, 4, 133,
+ /* 1580 */ 222, 223, 224, 275, 14, 211, 140, 141, 142, 143,
+ /* 1590 */ 127, 128, 121, 168, 286, 132, 73, 4, 127, 128,
+ /* 1600 */ 127, 128, 156, 157, 141, 142, 116, 4, 145, 38,
+ /* 1610 */ 147, 127, 128, 127, 128, 198, 199, 127, 128, 16,
+ /* 1620 */ 74, 175, 19, 249, 178, 4, 180, 181, 81, 82,
+ /* 1630 */ 83, 84, 109, 117, 87, 88, 89, 90, 91, 92,
+ /* 1640 */ 93, 94, 169, 96, 97, 98, 99, 100, 101, 102,
+ /* 1650 */ 103, 104, 105, 106, 107, 203, 298, 186, 121, 56,
+ /* 1660 */ 244, 175, 246, 179, 127, 128, 4, 203, 203, 217,
+ /* 1670 */ 124, 207, 69, 127, 128, 203, 139, 140, 226, 227,
+ /* 1680 */ 77, 217, 217, 156, 157, 117, 83, 235, 166, 217,
+ /* 1690 */ 122, 226, 227, 127, 128, 121, 203, 4, 226, 227,
+ /* 1700 */ 235, 127, 128, 100, 101, 168, 140, 235, 203, 116,
+ /* 1710 */ 217, 108, 117, 117, 117, 263, 264, 122, 122, 116,
+ /* 1720 */ 127, 128, 217, 117, 121, 219, 211, 203, 125, 119,
+ /* 1730 */ 127, 128, 117, 203, 168, 263, 133, 122, 286, 203,
+ /* 1740 */ 275, 217, 121, 140, 141, 142, 143, 217, 127, 128,
+ /* 1750 */ 4, 286, 4, 217, 319, 320, 226, 227, 286, 319,
+ /* 1760 */ 320, 187, 226, 227, 249, 235, 242, 274, 175, 319,
+ /* 1770 */ 320, 235, 266, 4, 79, 154, 4, 119, 175, 274,
+ /* 1780 */ 102, 178, 120, 180, 181, 203, 82, 83, 84, 127,
+ /* 1790 */ 128, 87, 88, 89, 90, 91, 92, 93, 94, 217,
/* 1800 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 1810 */ 106, 107, 4, 116, 116, 127, 128, 117, 117, 73,
- /* 1820 */ 275, 4, 117, 117, 16, 117, 50, 83, 84, 4,
- /* 1830 */ 285, 87, 88, 89, 90, 91, 92, 93, 94, 274,
+ /* 1810 */ 106, 107, 4, 219, 121, 116, 286, 117, 294, 73,
+ /* 1820 */ 127, 128, 286, 219, 16, 203, 117, 83, 84, 207,
+ /* 1830 */ 122, 87, 88, 89, 90, 91, 92, 93, 94, 217,
/* 1840 */ 96, 97, 98, 99, 100, 101, 102, 103, 104, 105,
- /* 1850 */ 106, 107, 203, 18, 4, 203, 203, 4, 127, 128,
- /* 1860 */ 173, 116, 116, 117, 56, 6, 217, 121, 203, 217,
- /* 1870 */ 217, 121, 4, 127, 128, 226, 227, 127, 128, 226,
- /* 1880 */ 227, 203, 217, 203, 235, 77, 140, 118, 235, 4,
- /* 1890 */ 140, 83, 8, 121, 116, 217, 4, 217, 50, 127,
- /* 1900 */ 128, 155, 156, 157, 116, 203, 4, 117, 100, 101,
- /* 1910 */ 179, 116, 263, 116, 4, 50, 108, 203, 168, 217,
- /* 1920 */ 116, 4, 242, 203, 116, 117, 16, 102, 203, 121,
- /* 1930 */ 137, 217, 207, 125, 285, 127, 128, 217, 285, 83,
- /* 1940 */ 203, 133, 217, 203, 127, 128, 226, 227, 140, 141,
- /* 1950 */ 142, 143, 127, 128, 217, 235, 151, 217, 125, 118,
- /* 1960 */ 145, 189, 13, 226, 227, 140, 56, 164, 203, 122,
- /* 1970 */ 4, 121, 235, 293, 121, 4, 274, 127, 128, 90,
- /* 1980 */ 127, 128, 217, 175, 150, 203, 178, 77, 180, 181,
- /* 1990 */ 140, 123, 175, 83, 90, 127, 128, 90, 4, 217,
- /* 2000 */ 175, 203, 90, 176, 24, 285, 121, 18, 226, 227,
- /* 2010 */ 100, 101, 127, 128, 274, 217, 4, 235, 108, 127,
- /* 2020 */ 128, 168, 285, 121, 226, 227, 116, 117, 16, 127,
- /* 2030 */ 128, 121, 203, 235, 203, 125, 150, 127, 128, 4,
- /* 2040 */ 155, 177, 140, 133, 127, 128, 217, 203, 217, 203,
- /* 2050 */ 140, 141, 142, 143, 4, 226, 227, 226, 227, 4,
- /* 2060 */ 168, 217, 4, 217, 235, 157, 235, 285, 56, 109,
- /* 2070 */ 226, 227, 226, 227, 109, 62, 4, 25, 203, 235,
- /* 2080 */ 163, 235, 203, 285, 51, 175, 207, 121, 178, 77,
- /* 2090 */ 180, 181, 217, 127, 128, 83, 217, 203, 127, 128,
- /* 2100 */ 122, 226, 227, 203, 51, 185, 140, 207, 145, 203,
- /* 2110 */ 235, 217, 100, 101, 285, 121, 285, 217, 4, 116,
- /* 2120 */ 108, 127, 128, 217, 115, 4, 165, 203, 116, 285,
- /* 2130 */ 16, 285, 125, 121, 140, 203, 116, 125, 117, 127,
- /* 2140 */ 128, 217, 203, 115, 203, 133, 175, 117, 49, 217,
- /* 2150 */ 226, 227, 140, 141, 142, 143, 217, 4, 217, 235,
- /* 2160 */ 285, 4, 127, 128, 4, 226, 227, 226, 227, 113,
- /* 2170 */ 56, 48, 216, 286, 235, 140, 235, 127, 128, 4,
- /* 2180 */ 274, 309, 127, 128, 4, 127, 128, 175, 116, 203,
- /* 2190 */ 178, 77, 180, 181, 182, 140, 203, 83, 269, 127,
- /* 2200 */ 128, 232, 4, 217, 203, 4, 232, 149, 311, 285,
- /* 2210 */ 217, 110, 226, 227, 100, 101, 311, 202, 217, 203,
- /* 2220 */ 4, 235, 108, 207, 285, 202, 285, 226, 227, 203,
- /* 2230 */ 116, 117, 16, 217, 202, 121, 235, 65, 188, 125,
- /* 2240 */ 202, 127, 128, 217, 4, 204, 203, 133, 127, 128,
- /* 2250 */ 207, 203, 226, 227, 140, 141, 142, 143, 4, 138,
- /* 2260 */ 217, 235, 4, 203, 4, 217, 4, 204, 206, 78,
- /* 2270 */ 209, 285, 56, 120, 226, 227, 203, 217, 122, 257,
- /* 2280 */ 127, 128, 203, 235, 127, 128, 285, 127, 128, 175,
- /* 2290 */ 217, 4, 178, 77, 180, 181, 217, 140, 119, 83,
- /* 2300 */ 140, 272, 127, 128, 156, 226, 227, 127, 128, 258,
- /* 2310 */ 251, 285, 4, 203, 235, 140, 100, 101, 173, 170,
- /* 2320 */ 140, 120, 4, 259, 108, 127, 128, 217, 127, 128,
- /* 2330 */ 171, 203, 116, 285, 16, 261, 172, 121, 203, 203,
- /* 2340 */ 107, 125, 231, 127, 128, 217, 203, 116, 4, 133,
- /* 2350 */ 4, 294, 217, 217, 226, 227, 140, 141, 142, 143,
- /* 2360 */ 217, 203, 4, 235, 285, 203, 107, 127, 128, 226,
- /* 2370 */ 227, 118, 289, 260, 56, 217, 182, 169, 235, 217,
- /* 2380 */ 35, 127, 128, 313, 186, 127, 128, 127, 128, 127,
- /* 2390 */ 128, 175, 203, 203, 178, 77, 180, 181, 203, 261,
- /* 2400 */ 140, 83, 57, 276, 27, 46, 217, 217, 63, 155,
- /* 2410 */ 276, 321, 217, 285, 127, 128, 226, 227, 100, 101,
- /* 2420 */ 4, 226, 227, 4, 203, 235, 108, 140, 285, 189,
- /* 2430 */ 235, 119, 4, 203, 116, 127, 128, 321, 217, 121,
- /* 2440 */ 272, 253, 157, 125, 326, 127, 128, 217, 193, 187,
- /* 2450 */ 4, 133, 228, 228, 109, 203, 226, 227, 140, 141,
- /* 2460 */ 142, 143, 117, 39, 145, 235, 120, 122, 203, 217,
- /* 2470 */ 238, 127, 128, 127, 128, 285, 168, 203, 203, 228,
- /* 2480 */ 285, 203, 217, 144, 140, 127, 128, 230, 238, 228,
- /* 2490 */ 145, 217, 217, 175, 203, 217, 178, 203, 180, 181,
- /* 2500 */ 231, 226, 227, 158, 203, 160, 161, 228, 217, 203,
- /* 2510 */ 235, 217, 228, 231, 169, 285, 171, 172, 217, 174,
- /* 2520 */ 226, 227, 119, 217, 228, 203, 203, 228, 203, 235,
- /* 2530 */ 206, 231, 226, 227, 176, 272, 120, 192, 203, 217,
- /* 2540 */ 217, 235, 217, 127, 128, 203, 127, 128, 119, 226,
- /* 2550 */ 227, 119, 217, 203, 206, 127, 128, 203, 235, 217,
- /* 2560 */ 285, 226, 227, 33, 203, 272, 203, 217, 226, 227,
- /* 2570 */ 235, 217, 126, 127, 128, 182, 300, 235, 217, 285,
- /* 2580 */ 217, 301, 119, 257, 174, 278, 245, 226, 227, 81,
- /* 2590 */ 119, 285, 278, 257, 175, 119, 235, 281, 203, 116,
- /* 2600 */ 203, 284, 203, 175, 145, 203, 278, 278, 285, 257,
- /* 2610 */ 245, 206, 217, 119, 217, 272, 217, 203, 206, 217,
- /* 2620 */ 285, 226, 227, 226, 227, 226, 227, 285, 226, 227,
- /* 2630 */ 235, 217, 235, 257, 235, 119, 272, 235, 203, 247,
- /* 2640 */ 226, 227, 78, 203, 119, 247, 285, 119, 247, 235,
- /* 2650 */ 119, 247, 217, 119, 176, 295, 272, 217, 119, 304,
- /* 2660 */ 20, 226, 227, 272, 119, 203, 226, 227, 272, 203,
- /* 2670 */ 235, 203, 304, 119, 119, 235, 306, 17, 306, 217,
- /* 2680 */ 285, 254, 285, 217, 285, 217, 256, 285, 226, 227,
- /* 2690 */ 229, 297, 226, 227, 226, 227, 290, 235, 260, 285,
- /* 2700 */ 203, 235, 260, 235, 286, 203, 297, 203, 271, 273,
- /* 2710 */ 229, 236, 240, 256, 217, 230, 273, 273, 201, 217,
- /* 2720 */ 285, 217, 257, 226, 227, 285, 219, 254, 226, 227,
- /* 2730 */ 226, 227, 235, 219, 219, 287, 203, 235, 219, 235,
- /* 2740 */ 299, 203, 252, 298, 246, 324, 237, 285, 237, 270,
- /* 2750 */ 217, 285, 226, 285, 241, 217, 203, 237, 226, 226,
- /* 2760 */ 227, 310, 203, 73, 226, 227, 4, 327, 235, 327,
- /* 2770 */ 217, 327, 327, 235, 327, 327, 217, 327, 327, 226,
- /* 2780 */ 227, 203, 285, 203, 327, 226, 227, 285, 235, 285,
- /* 2790 */ 327, 327, 327, 327, 235, 217, 327, 217, 327, 327,
- /* 2800 */ 327, 327, 327, 327, 226, 227, 226, 227, 327, 327,
- /* 2810 */ 327, 327, 327, 235, 327, 235, 327, 327, 285, 327,
- /* 2820 */ 327, 327, 327, 285, 327, 327, 327, 327, 327, 327,
- /* 2830 */ 327, 327, 327, 327, 327, 327, 327, 327, 285, 327,
- /* 2840 */ 327, 327, 327, 327, 285, 327, 327, 327, 327, 327,
- /* 2850 */ 327, 327, 327, 327, 327, 327, 327, 327, 327, 327,
- /* 2860 */ 327, 327, 327, 285, 327, 285,
+ /* 1850 */ 106, 107, 4, 323, 324, 203, 274, 203, 4, 111,
+ /* 1860 */ 266, 168, 116, 117, 56, 116, 159, 121, 203, 217,
+ /* 1870 */ 266, 217, 4, 127, 128, 127, 128, 117, 226, 227,
+ /* 1880 */ 226, 227, 217, 117, 4, 77, 140, 235, 193, 235,
+ /* 1890 */ 121, 83, 117, 121, 319, 320, 127, 128, 173, 127,
+ /* 1900 */ 128, 155, 156, 157, 203, 203, 58, 242, 100, 101,
+ /* 1910 */ 319, 320, 140, 203, 4, 263, 108, 263, 217, 217,
+ /* 1920 */ 203, 4, 116, 203, 116, 117, 16, 217, 117, 121,
+ /* 1930 */ 18, 203, 50, 125, 217, 127, 128, 217, 286, 203,
+ /* 1940 */ 286, 133, 4, 226, 227, 217, 226, 227, 140, 141,
+ /* 1950 */ 142, 143, 235, 217, 287, 235, 102, 116, 189, 294,
+ /* 1960 */ 203, 6, 226, 227, 207, 118, 56, 116, 120, 8,
+ /* 1970 */ 203, 235, 50, 306, 217, 127, 128, 116, 116, 111,
+ /* 1980 */ 263, 127, 128, 175, 217, 203, 178, 77, 180, 181,
+ /* 1990 */ 203, 203, 116, 83, 140, 127, 128, 50, 4, 217,
+ /* 2000 */ 4, 121, 117, 286, 217, 217, 286, 127, 128, 116,
+ /* 2010 */ 100, 101, 4, 83, 226, 227, 4, 151, 108, 4,
+ /* 2020 */ 140, 137, 286, 235, 125, 203, 116, 117, 16, 175,
+ /* 2030 */ 13, 121, 203, 203, 118, 125, 145, 127, 128, 217,
+ /* 2040 */ 122, 164, 4, 133, 127, 128, 217, 217, 203, 4,
+ /* 2050 */ 140, 141, 142, 143, 4, 226, 227, 140, 150, 121,
+ /* 2060 */ 90, 203, 217, 90, 235, 127, 128, 203, 56, 90,
+ /* 2070 */ 90, 226, 227, 203, 286, 217, 109, 4, 203, 176,
+ /* 2080 */ 235, 217, 4, 18, 203, 175, 24, 217, 178, 77,
+ /* 2090 */ 180, 181, 217, 155, 150, 83, 226, 227, 217, 157,
+ /* 2100 */ 203, 226, 227, 203, 207, 235, 177, 226, 227, 25,
+ /* 2110 */ 235, 109, 100, 101, 217, 286, 235, 217, 4, 109,
+ /* 2120 */ 108, 127, 128, 127, 128, 4, 62, 203, 116, 121,
+ /* 2130 */ 16, 286, 51, 121, 138, 127, 128, 125, 122, 127,
+ /* 2140 */ 128, 217, 127, 128, 51, 133, 203, 4, 140, 203,
+ /* 2150 */ 226, 227, 140, 141, 142, 143, 286, 203, 120, 235,
+ /* 2160 */ 217, 286, 168, 217, 149, 127, 128, 286, 203, 185,
+ /* 2170 */ 56, 217, 127, 128, 203, 145, 116, 127, 128, 165,
+ /* 2180 */ 226, 227, 217, 115, 203, 116, 125, 175, 217, 235,
+ /* 2190 */ 178, 77, 180, 181, 182, 203, 113, 83, 217, 154,
+ /* 2200 */ 127, 128, 4, 203, 4, 127, 128, 226, 227, 217,
+ /* 2210 */ 286, 117, 203, 140, 100, 101, 235, 217, 226, 227,
+ /* 2220 */ 4, 115, 108, 4, 117, 49, 217, 235, 4, 48,
+ /* 2230 */ 116, 117, 16, 269, 216, 121, 203, 203, 188, 125,
+ /* 2240 */ 286, 127, 128, 4, 287, 4, 310, 133, 127, 128,
+ /* 2250 */ 217, 217, 203, 4, 140, 141, 142, 143, 232, 226,
+ /* 2260 */ 227, 140, 312, 232, 186, 4, 217, 286, 235, 202,
+ /* 2270 */ 127, 128, 56, 110, 312, 226, 227, 203, 286, 202,
+ /* 2280 */ 204, 206, 203, 140, 235, 65, 204, 4, 203, 175,
+ /* 2290 */ 202, 217, 178, 77, 180, 181, 217, 202, 209, 83,
+ /* 2300 */ 226, 227, 217, 78, 4, 226, 227, 203, 122, 235,
+ /* 2310 */ 119, 226, 227, 272, 235, 156, 100, 101, 173, 286,
+ /* 2320 */ 235, 217, 4, 251, 108, 127, 128, 127, 128, 4,
+ /* 2330 */ 170, 203, 116, 171, 16, 286, 172, 121, 140, 120,
+ /* 2340 */ 140, 125, 107, 127, 128, 217, 127, 128, 4, 133,
+ /* 2350 */ 4, 127, 128, 257, 226, 227, 140, 141, 142, 143,
+ /* 2360 */ 286, 203, 121, 235, 140, 286, 127, 128, 127, 128,
+ /* 2370 */ 258, 286, 203, 231, 56, 217, 127, 128, 203, 259,
+ /* 2380 */ 35, 140, 295, 261, 226, 227, 217, 116, 127, 128,
+ /* 2390 */ 118, 175, 217, 235, 178, 77, 180, 181, 203, 203,
+ /* 2400 */ 107, 83, 57, 207, 121, 314, 203, 168, 63, 290,
+ /* 2410 */ 127, 128, 217, 217, 286, 182, 155, 203, 100, 101,
+ /* 2420 */ 217, 226, 227, 140, 203, 260, 108, 127, 128, 4,
+ /* 2430 */ 235, 217, 4, 169, 116, 203, 187, 276, 217, 121,
+ /* 2440 */ 261, 203, 46, 125, 286, 127, 128, 226, 227, 217,
+ /* 2450 */ 276, 133, 127, 128, 109, 217, 235, 322, 140, 141,
+ /* 2460 */ 142, 143, 117, 203, 120, 140, 322, 122, 203, 203,
+ /* 2470 */ 27, 127, 128, 127, 128, 119, 272, 217, 157, 253,
+ /* 2480 */ 203, 286, 217, 217, 207, 193, 226, 227, 203, 189,
+ /* 2490 */ 145, 228, 145, 175, 217, 235, 178, 327, 180, 181,
+ /* 2500 */ 238, 228, 217, 158, 203, 160, 161, 286, 203, 203,
+ /* 2510 */ 203, 226, 227, 39, 169, 203, 171, 172, 217, 174,
+ /* 2520 */ 235, 175, 217, 217, 217, 228, 203, 226, 227, 217,
+ /* 2530 */ 203, 144, 226, 227, 207, 231, 235, 192, 226, 227,
+ /* 2540 */ 217, 235, 228, 203, 217, 203, 286, 235, 238, 226,
+ /* 2550 */ 227, 231, 127, 128, 126, 127, 128, 217, 235, 217,
+ /* 2560 */ 203, 203, 203, 230, 207, 203, 207, 203, 226, 227,
+ /* 2570 */ 272, 286, 119, 206, 217, 217, 217, 235, 228, 217,
+ /* 2580 */ 228, 217, 228, 228, 226, 227, 119, 286, 226, 227,
+ /* 2590 */ 226, 227, 286, 235, 231, 206, 272, 235, 286, 235,
+ /* 2600 */ 203, 176, 203, 119, 301, 33, 203, 119, 182, 286,
+ /* 2610 */ 302, 174, 278, 245, 217, 81, 217, 257, 119, 278,
+ /* 2620 */ 217, 119, 203, 226, 227, 226, 227, 257, 286, 226,
+ /* 2630 */ 227, 116, 235, 284, 235, 145, 217, 257, 235, 278,
+ /* 2640 */ 245, 206, 203, 278, 286, 226, 227, 203, 286, 203,
+ /* 2650 */ 286, 272, 281, 206, 235, 119, 217, 257, 272, 119,
+ /* 2660 */ 247, 217, 78, 217, 203, 226, 227, 119, 247, 119,
+ /* 2670 */ 226, 227, 226, 227, 235, 119, 247, 247, 217, 235,
+ /* 2680 */ 119, 235, 176, 286, 296, 286, 272, 226, 227, 286,
+ /* 2690 */ 203, 20, 203, 119, 203, 305, 235, 203, 305, 272,
+ /* 2700 */ 119, 119, 119, 272, 217, 286, 217, 17, 217, 307,
+ /* 2710 */ 254, 217, 307, 226, 227, 226, 227, 226, 227, 203,
+ /* 2720 */ 226, 227, 235, 287, 235, 286, 235, 256, 260, 235,
+ /* 2730 */ 286, 203, 286, 217, 229, 260, 203, 271, 298, 298,
+ /* 2740 */ 291, 229, 226, 227, 236, 217, 273, 286, 230, 240,
+ /* 2750 */ 217, 235, 273, 273, 226, 227, 256, 285, 257, 226,
+ /* 2760 */ 227, 201, 203, 235, 254, 219, 219, 246, 235, 299,
+ /* 2770 */ 219, 219, 252, 286, 288, 286, 217, 286, 300, 325,
+ /* 2780 */ 286, 270, 237, 226, 226, 226, 227, 311, 73, 4,
+ /* 2790 */ 237, 237, 328, 328, 235, 328, 241, 328, 328, 328,
+ /* 2800 */ 328, 328, 286, 328, 328, 328, 328, 328, 328, 328,
+ /* 2810 */ 328, 328, 328, 328, 286, 328, 328, 328, 328, 286,
+ /* 2820 */ 328, 328, 328, 328, 328, 328, 328, 328, 328, 328,
+ /* 2830 */ 328, 328, 328, 328, 328, 328, 328, 328, 328, 328,
+ /* 2840 */ 328, 328, 328, 328, 328, 286,
};
-#define YY_SHIFT_USE_DFLT (-131)
-#define YY_SHIFT_COUNT (534)
-#define YY_SHIFT_MIN (-130)
-#define YY_SHIFT_MAX (2762)
+#define YY_SHIFT_USE_DFLT (-102)
+#define YY_SHIFT_COUNT (535)
+#define YY_SHIFT_MIN (-101)
+#define YY_SHIFT_MAX (2785)
static const short yy_shift_ofst[] = {
- /* 0 */ 1591, 808, 1446, 138, 1318, 1603, 1364, 2114, 2114, 2114,
- /* 10 */ 1260, 216, 2012, 2216, 2318, 2216, 2216, 2216, 2216, 2216,
- /* 20 */ 2216, 949, -4, 106, 1910, 1808, 2216, 2216, 2216, 2216,
- /* 30 */ 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2318, 2216,
+ /* 0 */ 690, 808, 1446, 138, 1318, 1603, 1364, 2114, 2114, 2114,
+ /* 10 */ 490, 216, 2012, 2318, 2216, 2216, 2216, 2216, 2216, 2216,
+ /* 20 */ 2216, 1523, -4, 106, 1910, 1808, 2216, 2216, 2216, 2216,
+ /* 30 */ 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216,
/* 40 */ 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216,
/* 50 */ 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216,
/* 60 */ 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216, 2216,
- /* 70 */ 2216, 2216, 1746, 1463, 1463, 587, 1400, 1400, 2446, 89,
- /* 80 */ 259, 592, 752, 2446, 2419, 2419, 2419, 2416, 2419, 494,
- /* 90 */ 494, 2258, 978, 338, 786, 142, 1994, 1772, 1853, 1885,
- /* 100 */ 1966, 1295, 1902, 1295, 1850, 1473, 1605, 752, 955, 2358,
- /* 110 */ 2428, 2428, 2428, 2428, 143, 2428, 2419, 2258, 2258, 978,
- /* 120 */ 750, 750, 1476, 519, 519, -43, 811, 1382, 1750, 1825,
- /* 130 */ 1534, 1348, 1261, 623, 1490, 285, 232, 1244, 232, 1425,
- /* 140 */ 127, 594, 220, 512, 2346, 2344, 2262, 2240, 2308, 2254,
- /* 150 */ 2287, 2201, 2260, 2198, 2180, 2175, 2160, 2055, 2050, 662,
- /* 160 */ 2153, 2157, 2121, 2058, 2035, 2072, 1134, 1104, 858, 858,
- /* 170 */ 858, 1892, 1917, 1971, 277, 277, 1731, 1817, 1530, 1197,
- /* 180 */ 1868, 762, 1688, 1662, 1566, 1432, 2258, 2258, 764, 764,
- /* 190 */ 1077, 498, 200, 2690, 2690, 2762, 2690, 2690, -131, -131,
- /* 200 */ -131, 421, 601, 601, 601, 601, 601, 601, 601, 601,
+ /* 70 */ 2216, 2216, 1746, 1463, 1463, 587, 1473, 1473, 2428, 89,
+ /* 80 */ 39, 1848, 1546, 2428, 1486, 1486, 1486, 1662, 1486, -33,
+ /* 90 */ -33, 635, 845, 338, 786, 142, 2283, 1769, 1693, 1938,
+ /* 100 */ 2241, 1593, 2008, 1593, 1880, 1772, 1621, 1546, 955, 2425,
+ /* 110 */ 2346, 2346, 2346, 2346, 414, 2346, 1486, 635, 635, 845,
+ /* 120 */ 1695, 1695, 1527, 519, 519, -43, 811, 1537, 1400, 1854,
+ /* 130 */ 1566, 1425, 1574, 529, 1471, 146, 530, 629, 530, 409,
+ /* 140 */ 429, 579, 187, 288, 2344, 2325, 2249, 2300, 2239, 2261,
+ /* 150 */ 2224, 2219, 2200, 2078, 2198, 2143, 2121, 2073, 2050, 2045,
+ /* 160 */ 2038, 1917, 1996, 2015, 1244, 1490, 1134, 1104, 858, 858,
+ /* 170 */ 858, 1994, 1136, 1386, 1014, 1014, 1484, 553, 1203, 828,
+ /* 180 */ 743, 757, 1868, 1748, 1449, 1198, 635, 635, 85, 85,
+ /* 190 */ 1413, 1342, 291, 2715, 2715, 2785, 2715, 2715, -102, -102,
+ /* 200 */ -102, 421, 601, 601, 601, 601, 601, 601, 601, 601,
/* 210 */ 601, 601, 571, 388, 704, 677, 1214, 1185, 1153, -73,
/* 220 */ 1122, 1091, 1060, 1028, 997, 963, 936, 909, 754, 1547,
/* 230 */ 1257, 1704, 1744, 1744, 482, -16, -16, -16, -16, -16,
- /* 240 */ -16, 204, 346, -35, -130, 406, 406, 862, 420, 1248,
- /* 250 */ 1248, 1248, 199, 193, 334, -8, 57, 784, 377, 1638,
- /* 260 */ 1562, 1602, 768, 1381, -67, 292, 589, 770, 734, 734,
- /* 270 */ -79, 1292, 695, 627, 734, 190, 375, 375, 77, 627,
- /* 280 */ 313, 313, 23, 131, 977, 2660, 2660, 2555, 2554, 2545,
- /* 290 */ 2640, 2640, 2539, 2478, 2534, 2564, 2531, 2564, 2528, 2564,
- /* 300 */ 2525, 2564, 2516, 2191, 2145, 2494, 2191, 2508, 2410, 2145,
- /* 310 */ 2410, 2459, 2483, 2476, 2410, 2145, 2471, 2508, 2410, 2145,
- /* 320 */ 2463, 2393, 2530, 2432, 2191, 2429, 2231, 2191, 2403, 2231,
- /* 330 */ 2319, 2319, 2319, 2319, 2424, 2231, 2319, 2339, 2319, 2424,
- /* 340 */ 2319, 2319, 2255, 2285, 2312, 2377, 2377, 2359, 2359, 2164,
- /* 350 */ 2208, 2194, 2253, 2259, 2231, 2233, 2233, 2164, 2159, 2149,
- /* 360 */ 2145, 2148, 2179, 2156, 2191, 2172, 2172, 2101, 2101, 2101,
- /* 370 */ 2101, -131, -131, -131, -131, -131, -131, -131, -131, -131,
- /* 380 */ -131, 2345, 40, 407, 798, 79, 533, 64, 343, 1256,
- /* 390 */ 1209, -74, 1116, -22, 1085, 1054, 844, 413, 340, -5,
- /* 400 */ 720, 401, 245, 209, -28, 65, 201, 87, -80, 167,
- /* 410 */ 2123, 2099, 2056, 2028, 2030, 2021, 2007, 2020, 1961, 2009,
- /* 420 */ 2003, 1963, 1920, 2053, 1978, 2033, 2013, 2052, 1965, 1960,
- /* 430 */ 1908, 1864, 1886, 1980, 1989, 1827, 1912, 1907, 1904, 1889,
- /* 440 */ 1834, 1847, 1803, 1949, 1815, 1841, 1833, 1856, 1805, 1793,
- /* 450 */ 1804, 1865, 1797, 1795, 1790, 1788, 1848, 1884, 1778, 1769,
- /* 460 */ 1859, 1745, 1776, 1835, 1708, 1687, 1698, 1706, 1705, 1701,
- /* 470 */ 1700, 1641, 1610, 1697, 1658, 1654, 1641, 1656, 1628, 1621,
- /* 480 */ 1572, 1608, 1606, 1553, 1604, 1677, 1674, 1540, 1553, 1611,
- /* 490 */ 1582, 1579, 1544, 1500, 1486, 1482, 1444, 1470, 1443, 1469,
- /* 500 */ 1320, 1309, 1282, 1290, 1286, 1362, 1202, 1172, 1068, 1082,
- /* 510 */ 986, 1129, 991, 954, 1024, 987, 991, 870, 842, 829,
- /* 520 */ 777, 812, 732, 608, 517, 574, 437, 419, 379, 242,
- /* 530 */ 358, 114, 76, 50, 11,
+ /* 240 */ -16, 204, 346, -101, 90, -27, -27, 751, 436, 268,
+ /* 250 */ 268, 268, 623, 328, 207, 190, 369, 392, 1398, 836,
+ /* 260 */ 830, 818, 213, 335, -67, 342, -79, 1615, 1230, 1331,
+ /* 270 */ 1331, 135, 1415, 120, 872, 1331, 584, 791, 791, 1194,
+ /* 280 */ 872, 684, 684, 1024, 991, 659, 2690, 2690, 2583, 2582,
+ /* 290 */ 2581, 2671, 2671, 2574, 2506, 2561, 2584, 2556, 2584, 2550,
+ /* 300 */ 2584, 2548, 2584, 2540, 2225, 2145, 2536, 2225, 2534, 2437,
+ /* 310 */ 2145, 2437, 2490, 2515, 2502, 2437, 2145, 2499, 2534, 2437,
+ /* 320 */ 2145, 2488, 2426, 2572, 2484, 2225, 2467, 2271, 2225, 2453,
+ /* 330 */ 2271, 2347, 2347, 2347, 2347, 2474, 2271, 2347, 2387, 2347,
+ /* 340 */ 2474, 2347, 2347, 2292, 2321, 2356, 2443, 2443, 2396, 2396,
+ /* 350 */ 2164, 2264, 2233, 2272, 2293, 2271, 2235, 2235, 2164, 2162,
+ /* 360 */ 2160, 2145, 2159, 2191, 2186, 2225, 2220, 2220, 2163, 2163,
+ /* 370 */ 2163, 2163, -102, -102, -102, -102, -102, -102, -102, -102,
+ /* 380 */ -102, -102, 2345, 525, 77, 518, 451, -15, 130, 169,
+ /* 390 */ 1596, 1595, 7, 1568, 435, 1434, 1314, 1211, 1207, 239,
+ /* 400 */ 609, 102, 1116, 788, 362, 488, 624, 87, -80, -44,
+ /* 410 */ 2181, 2176, 2083, 2106, 2107, 2094, 2061, 2069, 2014, 2068,
+ /* 420 */ 2060, 2030, 1984, 2093, 2016, 2081, 2064, 2084, 2010, 2002,
+ /* 430 */ 1942, 1929, 1944, 2062, 2065, 1967, 1903, 1980, 1979, 1973,
+ /* 440 */ 1970, 1908, 1918, 1877, 2017, 1891, 1916, 1899, 1930, 1866,
+ /* 450 */ 1884, 1893, 1947, 1876, 1862, 1885, 1861, 1922, 1961, 1851,
+ /* 460 */ 1847, 1955, 1841, 1882, 1912, 1811, 1725, 1806, 1775, 1766,
+ /* 470 */ 1760, 1709, 1708, 1707, 1749, 1700, 1699, 1708, 1678, 1658,
+ /* 480 */ 1610, 1522, 1606, 1597, 1453, 1516, 1571, 1570, 1404, 1453,
+ /* 490 */ 1558, 1552, 1534, 1517, 1469, 1414, 1408, 1346, 1338, 1289,
+ /* 500 */ 1279, 1148, 1101, 1112, 1077, 1054, 1125, 910, 884, 869,
+ /* 510 */ 905, 822, 961, 618, 854, 863, 862, 618, 763, 580,
+ /* 520 */ 655, 595, 430, 562, 549, 452, 420, 352, 287, 265,
+ /* 530 */ 219, 215, 201, 63, 46, 43,
};
-#define YY_REDUCE_USE_DFLT (-105)
-#define YY_REDUCE_COUNT (380)
-#define YY_REDUCE_MIN (-104)
-#define YY_REDUCE_MAX (2580)
+#define YY_REDUCE_USE_DFLT (-205)
+#define YY_REDUCE_COUNT (381)
+#define YY_REDUCE_MIN (-204)
+#define YY_REDUCE_MAX (2560)
static const short yy_reduce_ofst[] = {
- /* 0 */ 154, 119, 1164, 619, 1252, 1189, 176, 1167, 329, -45,
- /* 10 */ -104, 1649, -101, 1545, 1481, 1479, 1464, 1452, 1314, 1298,
- /* 20 */ 183, 691, 2580, 2578, 2559, 2553, 2538, 2533, 2504, 2502,
- /* 30 */ 2497, 2468, 2466, 2462, 2440, 2435, 2414, 2402, 2399, 2397,
- /* 40 */ 2395, 2361, 2342, 2335, 2323, 2306, 2294, 2275, 2230, 2195,
- /* 50 */ 2190, 2143, 2128, 2079, 2048, 2026, 2001, 1986, 1941, 1939,
- /* 60 */ 1924, 1875, 1846, 1844, 1831, 1829, 1798, 1782, 1737, 1720,
- /* 70 */ 1653, 660, 622, 18, -23, 513, 428, 54, 337, 615,
- /* 80 */ 721, 1126, 525, 1538, 1680, 1492, 1468, 760, -102, 683,
- /* 90 */ 335, 507, 348, 1111, 515, 1395, 2043, 2016, 1900, 1879,
- /* 100 */ 1725, 1204, 1550, 920, 1375, 1125, 696, 1193, 439, 778,
- /* 110 */ 1906, 1740, 1702, 1565, 405, 1283, 667, 62, -84, 736,
- /* 120 */ 540, 240, 483, 1493, 1431, 1311, 373, 2363, 2354, 2322,
- /* 130 */ 1894, 1894, 2350, 2325, 2136, 1932, 1227, 1714, 723, 1894,
- /* 140 */ 1454, 1394, 2322, 2301, 2291, 1894, 1894, 1894, 1894, 1894,
- /* 150 */ 1894, 1894, 2278, 1894, 1894, 1894, 1894, 2274, 1894, 1894,
- /* 160 */ 1894, 2265, 2252, 2221, 2189, 2162, 2158, 2135, 1357, 1061,
- /* 170 */ 998, 2110, 2073, 1665, 1346, 1296, 2060, 1993, 1894, 1765,
- /* 180 */ 1678, 1376, 1652, 1557, 1480, 1278, 1251, 1225, 1266, 1217,
- /* 190 */ 971, 1319, 469, 1307, 1302, 831, 1233, 1168, 158, 1201,
- /* 200 */ 645, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887,
- /* 210 */ 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887,
- /* 220 */ 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887,
- /* 230 */ 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887, 1887,
- /* 240 */ 1887, 1887, 1887, 1887, 2513, 2532, 2526, 2451, 2451, 2520,
- /* 250 */ 2511, 2509, 2479, 2421, 2498, 2490, 2448, 2441, 2445, 2519,
- /* 260 */ 2515, 2514, 1887, 2507, 2473, 2517, 2465, 2457, 2444, 2443,
- /* 270 */ 2485, 2472, 2475, 2481, 2436, 2437, 2442, 2438, 2406, 2461,
- /* 280 */ 2409, 2394, 2418, 2430, 2427, 2372, 2370, 2263, 2396, 2391,
- /* 290 */ 2368, 2355, 2384, 2360, 2263, 2404, 2263, 2401, 2263, 2398,
- /* 300 */ 2263, 2392, 2364, 2412, 2376, 2343, 2405, 2365, 2329, 2352,
- /* 310 */ 2328, 2317, 2316, 2263, 2314, 2336, 2263, 2341, 2307, 2326,
- /* 320 */ 2263, 2280, 2276, 2293, 2348, 2263, 2300, 2324, 2263, 2282,
- /* 330 */ 2299, 2296, 2284, 2279, 2250, 2269, 2261, 2257, 2251, 2232,
- /* 340 */ 2225, 2224, 2118, 2188, 2168, 2116, 2090, 2134, 2127, 2138,
- /* 350 */ 2113, 2083, 2070, 2057, 2111, 1887, 1887, 2074, 2064, 2051,
- /* 360 */ 2022, 2059, 2029, 2061, 2062, 2063, 2041, 2038, 2032, 2023,
- /* 370 */ 2015, 1905, 1897, 1872, 1974, 1969, 1929, 1887, 1887, 1887,
- /* 380 */ 1956,
+ /* 0 */ 538, 119, 1162, 1175, 660, 1530, 175, 1452, 1252, -45,
+ /* 10 */ -104, 1472, 1182, 1465, 1308, 1717, 1283, 1195, 1654, 1652,
+ /* 20 */ 672, 691, 2559, 2533, 2528, 2516, 2494, 2491, 2489, 2487,
+ /* 30 */ 2461, 2446, 2444, 2439, 2419, 2403, 2399, 2397, 2364, 2362,
+ /* 40 */ 2358, 2342, 2323, 2312, 2306, 2301, 2285, 2260, 2221, 2195,
+ /* 50 */ 2158, 2128, 2085, 2079, 2074, 2049, 2033, 1992, 1981, 1954,
+ /* 60 */ 1924, 1881, 1875, 1870, 1845, 1829, 1788, 1736, 1720, 1536,
+ /* 70 */ 172, -92, 616, 331, 37, 513, 424, -24, 152, 611,
+ /* 80 */ 918, 613, 521, 434, 1665, 1524, 1190, -77, 673, 1358,
+ /* 90 */ 66, 150, -150, 695, -106, 327, 2359, 2357, 2327, 2277,
+ /* 100 */ 2196, 1232, 1897, 920, 1757, 1622, 1464, 508, 1174, 777,
+ /* 110 */ 1582, 1505, 1493, 1199, 1099, 1189, 123, 183, 855, -118,
+ /* 120 */ 651, 604, 650, 645, 610, 1667, -204, 2340, 2307, 2214,
+ /* 130 */ 1787, 1787, 2305, 2266, 2265, 2238, 1416, 2232, 1313, 1787,
+ /* 140 */ 1604, 1591, 2214, 2203, 2175, 1787, 1787, 1787, 1787, 1787,
+ /* 150 */ 1787, 1787, 2169, 1787, 1787, 1787, 1787, 2104, 1787, 1787,
+ /* 160 */ 1787, 2034, 2009, 2000, 1971, 1965, 1946, 1943, 1594, 1506,
+ /* 170 */ 1061, 1900, 1864, 1858, 1575, 1450, 1830, 1822, 1787, 1782,
+ /* 180 */ 1767, 345, 1728, 1710, 1702, 1701, 1179, 428, 1440, 1435,
+ /* 190 */ 1417, 1515, 1241, 1374, 1306, 1149, 1284, 1233, 796, 1201,
+ /* 200 */ 1172, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957,
+ /* 210 */ 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957,
+ /* 220 */ 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957,
+ /* 230 */ 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957, 1957,
+ /* 240 */ 1957, 1957, 1957, 1957, 2555, 2558, 2557, 2476, 2476, 2554,
+ /* 250 */ 2553, 2545, 2511, 2454, 2521, 2520, 2486, 2478, 2470, 2552,
+ /* 260 */ 2551, 2547, 1957, 2546, 2510, 2560, 2501, 2472, 2500, 2480,
+ /* 270 */ 2479, 2518, 2509, 2508, 2512, 2473, 2466, 2475, 2468, 2449,
+ /* 280 */ 2505, 2441, 2440, 2436, 2471, 2456, 2405, 2402, 2298, 2431,
+ /* 290 */ 2427, 2393, 2390, 2414, 2388, 2298, 2430, 2298, 2429, 2298,
+ /* 300 */ 2421, 2298, 2413, 2386, 2447, 2400, 2379, 2435, 2395, 2365,
+ /* 310 */ 2380, 2361, 2349, 2371, 2298, 2341, 2370, 2298, 2368, 2334,
+ /* 320 */ 2360, 2298, 2308, 2303, 2324, 2389, 2298, 2363, 2367, 2298,
+ /* 330 */ 2320, 2355, 2354, 2352, 2350, 2310, 2304, 2314, 2333, 2297,
+ /* 340 */ 2262, 2273, 2263, 2170, 2226, 2204, 2144, 2135, 2174, 2161,
+ /* 350 */ 2179, 2165, 2119, 2091, 2087, 2142, 1957, 1957, 2122, 2120,
+ /* 360 */ 2112, 2096, 2072, 2041, 2089, 2075, 2082, 2076, 2095, 2088,
+ /* 370 */ 2077, 2067, 1962, 1950, 1936, 2031, 2026, 1964, 1957, 1957,
+ /* 380 */ 1957, 2018,
};
static const YYACTIONTYPE yy_default[] = {
- /* 0 */ 875, 1195, 1195, 1315, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 10 */ 1315, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 20 */ 1195, 1315, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 30 */ 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 40 */ 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 50 */ 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 60 */ 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195, 1195,
- /* 70 */ 1195, 1195, 1059, 1357, 1357, 1357, 1334, 1334, 1357, 1052,
- /* 80 */ 1357, 1357, 903, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 90 */ 1357, 1357, 926, 1048, 916, 1059, 1357, 1357, 1357, 1357,
- /* 100 */ 1357, 1121, 1135, 1121, 1113, 1102, 1357, 1357, 1357, 1231,
- /* 110 */ 1129, 1129, 1129, 1129, 999, 1129, 1357, 1357, 1357, 1357,
- /* 120 */ 1163, 1162, 1357, 1087, 1087, 1197, 1357, 1284, 1289, 1156,
- /* 130 */ 1357, 1357, 1357, 1357, 1357, 1122, 1357, 1357, 1357, 1060,
- /* 140 */ 1048, 1334, 1156, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 150 */ 1357, 1357, 1357, 1357, 1136, 1114, 1103, 1357, 1357, 1357,
- /* 160 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1048, 1048,
- /* 170 */ 1048, 1357, 1357, 1357, 1334, 1334, 1357, 1158, 1357, 1357,
- /* 180 */ 1357, 913, 1357, 1357, 1357, 881, 1357, 1357, 1334, 1334,
- /* 190 */ 875, 1315, 1081, 1315, 1315, 921, 1315, 1315, 1308, 1038,
- /* 200 */ 1038, 1097, 1120, 1119, 1118, 1117, 1065, 1107, 1095, 1099,
- /* 210 */ 1208, 1098, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
- /* 220 */ 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
- /* 230 */ 1197, 1165, 1179, 1164, 1172, 1184, 1173, 1178, 1177, 1176,
- /* 240 */ 1167, 1166, 1168, 1169, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 250 */ 1357, 1357, 1051, 1357, 1357, 1021, 1357, 1357, 1258, 1357,
- /* 260 */ 1357, 928, 1170, 1357, 1036, 884, 1106, 1049, 1077, 1077,
- /* 270 */ 966, 990, 950, 1087, 1077, 1067, 1081, 1081, 1203, 1087,
- /* 280 */ 1357, 1357, 1197, 1049, 1036, 1299, 1299, 1068, 1068, 1068,
- /* 290 */ 1283, 1283, 1068, 1231, 1068, 1012, 1068, 1012, 1068, 1012,
- /* 300 */ 1068, 1012, 1068, 910, 1106, 1068, 910, 1003, 1109, 1106,
- /* 310 */ 1109, 1141, 1125, 1068, 1109, 1106, 1068, 1003, 1109, 1106,
- /* 320 */ 1068, 1265, 1263, 1068, 910, 1068, 1216, 910, 1068, 1216,
- /* 330 */ 1001, 1001, 1001, 1001, 982, 1216, 1001, 966, 1001, 982,
- /* 340 */ 1001, 1001, 1353, 1357, 1068, 1344, 1344, 1090, 1090, 1096,
- /* 350 */ 1081, 1357, 1357, 1222, 1216, 1183, 1171, 1096, 1094, 1091,
- /* 360 */ 1106, 1357, 1068, 985, 910, 892, 892, 880, 880, 880,
- /* 370 */ 880, 1312, 1312, 1308, 968, 968, 1054, 1182, 1181, 1180,
- /* 380 */ 937, 1196, 1357, 1357, 1357, 1357, 1357, 1357, 1232, 1357,
- /* 390 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 400 */ 1357, 1357, 1357, 1357, 1357, 1318, 1357, 1357, 1357, 1357,
- /* 410 */ 1357, 876, 1357, 1357, 1357, 1357, 1357, 1302, 1357, 1357,
- /* 420 */ 1357, 1357, 1357, 1357, 1262, 1261, 1357, 1357, 1357, 1357,
- /* 430 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 440 */ 1357, 1110, 1357, 1250, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 450 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 460 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 470 */ 1357, 1024, 1030, 1357, 1357, 1357, 1025, 1357, 1357, 1154,
- /* 480 */ 1357, 1357, 1357, 1206, 1357, 1357, 1357, 1357, 1092, 1357,
- /* 490 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1357,
- /* 500 */ 1357, 1357, 1357, 1350, 1082, 1357, 1357, 1357, 1198, 1357,
- /* 510 */ 1196, 1357, 1317, 1357, 1357, 1357, 1316, 1357, 1357, 1357,
- /* 520 */ 1357, 1357, 1357, 1357, 1357, 1357, 1357, 1155, 1154, 1198,
- /* 530 */ 919, 899, 1357, 890, 1357, 872, 877, 1301, 1298, 1295,
- /* 540 */ 1300, 1294, 1296, 1293, 1297, 1292, 1290, 1291, 1288, 1286,
- /* 550 */ 1285, 1287, 1282, 1278, 1238, 1236, 1234, 1243, 1242, 1241,
- /* 560 */ 1240, 1239, 1235, 1233, 1237, 1229, 1228, 1132, 1111, 1100,
- /* 570 */ 1019, 1277, 1275, 1276, 1227, 1225, 1226, 1018, 1017, 1016,
- /* 580 */ 1011, 1010, 1009, 1008, 1305, 1314, 1313, 1311, 1310, 1309,
- /* 590 */ 1303, 1304, 1214, 1213, 1211, 1210, 1212, 912, 1254, 1257,
- /* 600 */ 1256, 1255, 1260, 1259, 1252, 1264, 1269, 1268, 1273, 1272,
- /* 610 */ 1271, 1270, 1267, 1249, 1140, 1139, 1137, 1134, 1144, 1143,
- /* 620 */ 1142, 1133, 1126, 1138, 1116, 1124, 1123, 1112, 1115, 1004,
- /* 630 */ 1105, 1101, 1104, 1020, 1253, 1015, 1014, 1013, 911, 902,
- /* 640 */ 1070, 901, 900, 915, 988, 989, 997, 1000, 995, 998,
- /* 650 */ 994, 993, 992, 996, 991, 987, 918, 917, 927, 981,
- /* 660 */ 964, 953, 920, 955, 952, 951, 956, 973, 972, 979,
- /* 670 */ 978, 977, 976, 975, 971, 974, 970, 969, 957, 949,
- /* 680 */ 948, 967, 947, 984, 983, 980, 946, 1007, 1006, 1005,
- /* 690 */ 1002, 945, 944, 943, 942, 941, 940, 1194, 1356, 1352,
- /* 700 */ 1355, 1354, 1351, 1193, 1199, 1187, 1185, 1022, 1033, 1032,
- /* 710 */ 1031, 1028, 1029, 1043, 1041, 1040, 1039, 1076, 1075, 1074,
- /* 720 */ 1073, 1072, 1071, 1064, 1062, 1057, 1056, 1063, 1061, 1058,
- /* 730 */ 1079, 1080, 1078, 1055, 1047, 1045, 1046, 1044, 1131, 1128,
- /* 740 */ 1130, 1127, 1066, 1053, 1050, 1037, 1332, 1330, 1333, 1331,
- /* 750 */ 1329, 1337, 1339, 1338, 1343, 1341, 1340, 1336, 1349, 1348,
- /* 760 */ 1347, 1346, 1345, 1335, 1342, 1328, 1327, 1326, 1325, 1084,
- /* 770 */ 1089, 1088, 1083, 1027, 1186, 1196, 1190, 1323, 1321, 1324,
- /* 780 */ 1320, 1319, 1219, 1221, 1224, 1223, 1220, 1086, 1085, 1218,
- /* 790 */ 1217, 1322, 1189, 1161, 933, 931, 932, 1246, 1245, 1248,
- /* 800 */ 1247, 1244, 935, 934, 930, 929, 1159, 1153, 1152, 1274,
- /* 810 */ 1191, 1192, 1151, 1157, 1149, 1148, 1147, 1175, 1174, 1160,
- /* 820 */ 1150, 922, 1026, 1023, 1188, 1146, 1069, 1145, 963, 962,
- /* 830 */ 961, 960, 959, 958, 1035, 1034, 939, 954, 938, 936,
- /* 840 */ 914, 904, 909, 907, 908, 906, 905, 897, 894, 896,
- /* 850 */ 893, 898, 895, 891, 889, 888, 887, 886, 885, 925,
- /* 860 */ 924, 923, 919, 883, 882, 879, 878, 874, 873, 871,
+ /* 0 */ 876, 1197, 1197, 1319, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 10 */ 1319, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 20 */ 1197, 1319, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 30 */ 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 40 */ 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 50 */ 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 60 */ 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197, 1197,
+ /* 70 */ 1197, 1197, 1060, 1361, 1361, 1361, 1338, 1338, 1361, 1053,
+ /* 80 */ 1361, 1361, 904, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 90 */ 1361, 1361, 927, 1049, 917, 1060, 1361, 1361, 1361, 1361,
+ /* 100 */ 1361, 1122, 1137, 1122, 1114, 1103, 1361, 1361, 1361, 1235,
+ /* 110 */ 1130, 1130, 1130, 1130, 1000, 1130, 1361, 1361, 1361, 1361,
+ /* 120 */ 1165, 1164, 1361, 1088, 1088, 1199, 1361, 1288, 1293, 1158,
+ /* 130 */ 1361, 1361, 1361, 1361, 1361, 1123, 1361, 1361, 1361, 1061,
+ /* 140 */ 1049, 1338, 1158, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 150 */ 1361, 1361, 1361, 1361, 1138, 1115, 1104, 1361, 1361, 1361,
+ /* 160 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1049, 1049,
+ /* 170 */ 1049, 1361, 1361, 1361, 1338, 1338, 1361, 1160, 1361, 1361,
+ /* 180 */ 1361, 914, 1361, 1361, 1361, 882, 1361, 1361, 1338, 1338,
+ /* 190 */ 876, 1319, 1082, 1319, 1319, 922, 1319, 1319, 1312, 1039,
+ /* 200 */ 1039, 1098, 1121, 1120, 1119, 1118, 1066, 1108, 1096, 1100,
+ /* 210 */ 1212, 1099, 1199, 1199, 1199, 1199, 1199, 1199, 1199, 1199,
+ /* 220 */ 1199, 1199, 1199, 1199, 1199, 1199, 1199, 1199, 1199, 1199,
+ /* 230 */ 1199, 1167, 1181, 1166, 1174, 1186, 1175, 1180, 1179, 1178,
+ /* 240 */ 1169, 1168, 1170, 1171, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 250 */ 1361, 1361, 1052, 1361, 1361, 1022, 1361, 1361, 1262, 1361,
+ /* 260 */ 1361, 929, 1172, 1361, 1037, 885, 1107, 1201, 1050, 1078,
+ /* 270 */ 1078, 967, 991, 951, 1088, 1078, 1068, 1082, 1082, 1207,
+ /* 280 */ 1088, 1361, 1361, 1199, 1050, 1037, 1303, 1303, 1069, 1069,
+ /* 290 */ 1069, 1287, 1287, 1069, 1235, 1069, 1013, 1069, 1013, 1069,
+ /* 300 */ 1013, 1069, 1013, 1069, 911, 1107, 1069, 911, 1004, 1110,
+ /* 310 */ 1107, 1110, 1143, 1126, 1069, 1110, 1107, 1069, 1004, 1110,
+ /* 320 */ 1107, 1069, 1269, 1267, 1069, 911, 1069, 1220, 911, 1069,
+ /* 330 */ 1220, 1002, 1002, 1002, 1002, 983, 1220, 1002, 967, 1002,
+ /* 340 */ 983, 1002, 1002, 1357, 1361, 1069, 1348, 1348, 1091, 1091,
+ /* 350 */ 1097, 1082, 1361, 1361, 1226, 1220, 1185, 1173, 1097, 1095,
+ /* 360 */ 1092, 1107, 1361, 1069, 986, 911, 893, 893, 881, 881,
+ /* 370 */ 881, 881, 1316, 1316, 1312, 969, 969, 1055, 1184, 1183,
+ /* 380 */ 1182, 938, 1198, 1361, 1361, 1361, 1361, 1361, 1361, 1236,
+ /* 390 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 400 */ 1361, 1361, 1361, 1361, 1361, 1322, 1361, 1361, 1361, 1361,
+ /* 410 */ 1361, 877, 1361, 1361, 1361, 1361, 1361, 1306, 1361, 1361,
+ /* 420 */ 1361, 1361, 1361, 1361, 1266, 1265, 1361, 1361, 1361, 1361,
+ /* 430 */ 1361, 1361, 1361, 1361, 1361, 1127, 1361, 1361, 1361, 1361,
+ /* 440 */ 1361, 1361, 1111, 1361, 1254, 1361, 1361, 1361, 1361, 1361,
+ /* 450 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 460 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 470 */ 1361, 1361, 1025, 1031, 1361, 1361, 1361, 1026, 1361, 1361,
+ /* 480 */ 1156, 1361, 1361, 1361, 1210, 1361, 1361, 1361, 1361, 1093,
+ /* 490 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361,
+ /* 500 */ 1361, 1361, 1361, 1361, 1354, 1083, 1361, 1361, 1361, 1200,
+ /* 510 */ 1361, 1198, 1361, 1321, 1361, 1361, 1361, 1320, 1361, 1361,
+ /* 520 */ 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1361, 1157, 1156,
+ /* 530 */ 1200, 920, 900, 1361, 891, 1361, 873, 878, 1305, 1302,
+ /* 540 */ 1299, 1304, 1298, 1300, 1297, 1301, 1296, 1294, 1295, 1292,
+ /* 550 */ 1290, 1289, 1291, 1286, 1282, 1242, 1240, 1238, 1247, 1246,
+ /* 560 */ 1245, 1244, 1243, 1239, 1237, 1241, 1233, 1232, 1133, 1112,
+ /* 570 */ 1101, 1020, 1281, 1279, 1280, 1231, 1229, 1230, 1019, 1018,
+ /* 580 */ 1017, 1012, 1011, 1010, 1009, 1309, 1318, 1317, 1315, 1314,
+ /* 590 */ 1313, 1307, 1308, 1218, 1217, 1215, 1214, 1216, 913, 1258,
+ /* 600 */ 1261, 1260, 1259, 1264, 1263, 1256, 1268, 1273, 1272, 1277,
+ /* 610 */ 1276, 1275, 1274, 1271, 1253, 1142, 1141, 1139, 1135, 1146,
+ /* 620 */ 1145, 1144, 1134, 1136, 1140, 1117, 1125, 1124, 1113, 1116,
+ /* 630 */ 1005, 1106, 1102, 1105, 1021, 1257, 1016, 1015, 1014, 912,
+ /* 640 */ 903, 1071, 902, 901, 916, 989, 990, 998, 1001, 996,
+ /* 650 */ 999, 995, 994, 993, 997, 992, 988, 919, 918, 928,
+ /* 660 */ 982, 965, 954, 921, 956, 953, 952, 957, 974, 973,
+ /* 670 */ 980, 979, 978, 977, 976, 972, 975, 971, 970, 958,
+ /* 680 */ 950, 949, 968, 948, 985, 984, 981, 947, 1008, 1007,
+ /* 690 */ 1006, 1003, 946, 945, 944, 943, 942, 941, 1196, 1360,
+ /* 700 */ 1356, 1359, 1358, 1355, 1195, 1203, 1189, 1187, 1023, 1034,
+ /* 710 */ 1033, 1032, 1029, 1030, 1044, 1042, 1041, 1040, 1077, 1076,
+ /* 720 */ 1075, 1074, 1073, 1072, 1065, 1063, 1058, 1057, 1064, 1062,
+ /* 730 */ 1059, 1080, 1081, 1079, 1056, 1048, 1046, 1047, 1045, 1132,
+ /* 740 */ 1129, 1131, 1128, 1067, 1054, 1051, 1038, 1336, 1334, 1337,
+ /* 750 */ 1335, 1333, 1341, 1343, 1342, 1347, 1345, 1344, 1340, 1353,
+ /* 760 */ 1352, 1351, 1350, 1349, 1339, 1346, 1332, 1331, 1330, 1329,
+ /* 770 */ 1085, 1090, 1089, 1084, 1028, 1188, 1198, 1192, 1327, 1325,
+ /* 780 */ 1328, 1324, 1323, 1223, 1225, 1228, 1227, 1224, 1087, 1086,
+ /* 790 */ 1222, 1221, 1326, 1191, 1163, 934, 932, 933, 1250, 1249,
+ /* 800 */ 1252, 1251, 1248, 936, 935, 931, 930, 1161, 1155, 1154,
+ /* 810 */ 1278, 1193, 1194, 1153, 1159, 1151, 1150, 1149, 1177, 1176,
+ /* 820 */ 1162, 1152, 923, 1027, 1024, 1190, 1148, 1070, 1147, 964,
+ /* 830 */ 963, 962, 961, 960, 959, 1036, 1035, 940, 955, 939,
+ /* 840 */ 937, 915, 905, 910, 908, 909, 907, 906, 898, 895,
+ /* 850 */ 897, 894, 899, 896, 892, 890, 889, 888, 887, 886,
+ /* 860 */ 926, 925, 924, 920, 884, 883, 880, 879, 875, 874,
+ /* 870 */ 872,
};
/* The next table maps tokens into fallback tokens. If a construct
@@ -1353,17 +1350,17 @@ static const char *const yyTokenName[] = {
"dbnm", "indexed_opt", "idlist", "sortlist",
"nulls", "delete_stmt", "returning", "update_stmt",
"setlist", "idlist_opt", "insert_stmt", "insert_cmd",
- "upsert", "exprx", "not_opt", "likeop",
- "case_operand", "case_exprlist", "case_else", "filter_over",
- "uniqueflag", "idxlist_single", "collate", "vinto",
- "nmnum", "number", "trigger_time", "trigger_event",
- "foreach_clause", "when_clause", "trigger_cmd_list", "trigger_cmd",
- "database_kw_opt", "key_opt", "kwcolumn_opt", "create_vtab",
- "vtabarglist", "vtabarg", "vtabargtoken", "anylist",
- "wqlist", "wqas", "wqcte", "windowdefn_list",
- "windowdefn", "window", "frame_opt", "range_or_rows",
- "frame_bound_s", "frame_exclude_opt", "frame_bound_e", "frame_bound",
- "frame_exclude", "filter_clause", "over_clause",
+ "upsert", "rp_opt", "exprx", "not_opt",
+ "likeop", "case_operand", "case_exprlist", "case_else",
+ "filter_over", "uniqueflag", "idxlist_single", "collate",
+ "vinto", "nmnum", "number", "trigger_time",
+ "trigger_event", "foreach_clause", "when_clause", "trigger_cmd_list",
+ "trigger_cmd", "database_kw_opt", "key_opt", "kwcolumn_opt",
+ "create_vtab", "vtabarglist", "vtabarg", "vtabargtoken",
+ "anylist", "wqlist", "wqas", "wqcte",
+ "windowdefn_list", "windowdefn", "window", "frame_opt",
+ "range_or_rows", "frame_bound_s", "frame_exclude_opt", "frame_bound_e",
+ "frame_bound", "frame_exclude", "filter_clause", "over_clause",
};
#endif /* NDEBUG */
@@ -1636,228 +1633,231 @@ static const char *const yyRuleName[] = {
/* 262 */ "cmd ::= insert_stmt",
/* 263 */ "insert_stmt ::= with insert_cmd INTO fullname idlist_opt select upsert returning",
/* 264 */ "insert_stmt ::= with insert_cmd INTO fullname idlist_opt DEFAULT VALUES returning",
- /* 265 */ "insert_stmt ::= with insert_cmd INTO",
- /* 266 */ "insert_stmt ::= with insert_cmd INTO nm DOT",
- /* 267 */ "insert_stmt ::= with insert_cmd INTO ID_DB|ID_TAB",
- /* 268 */ "insert_stmt ::= with insert_cmd INTO nm DOT ID_TAB",
- /* 269 */ "insert_cmd ::= INSERT orconf",
- /* 270 */ "insert_cmd ::= REPLACE",
- /* 271 */ "upsert ::=",
- /* 272 */ "upsert ::= ON CONFLICT LP sortlist RP where_opt DO UPDATE SET setlist where_opt",
- /* 273 */ "upsert ::= ON CONFLICT LP sortlist RP where_opt DO NOTHING",
- /* 274 */ "upsert ::= ON CONFLICT DO NOTHING",
- /* 275 */ "exprx ::= expr not_opt IN ID_DB",
- /* 276 */ "exprx ::= expr not_opt IN nm DOT ID_TAB",
- /* 277 */ "exprx ::= ID_DB|ID_TAB|ID_COL|ID_FN",
- /* 278 */ "exprx ::= tnm DOT ID_TAB|ID_COL",
- /* 279 */ "exprx ::= tnm DOT nm DOT ID_COL",
- /* 280 */ "exprx ::= expr COLLATE ID_COLLATE",
- /* 281 */ "exprx ::= RAISE LP raisetype COMMA ID_ERR_MSG RP",
- /* 282 */ "exprx ::= CTIME_KW",
- /* 283 */ "exprx ::= LP nexprlist RP",
- /* 284 */ "exprx ::= tnm",
- /* 285 */ "exprx ::= tnm DOT nm",
- /* 286 */ "exprx ::= tnm DOT",
- /* 287 */ "exprx ::= tnm DOT nm DOT nm",
- /* 288 */ "exprx ::= tnm DOT nm DOT",
- /* 289 */ "exprx ::= VARIABLE",
- /* 290 */ "exprx ::= expr COLLATE ids",
- /* 291 */ "exprx ::= CAST LP expr AS typetoken RP",
- /* 292 */ "exprx ::= ID LP distinct exprlist RP",
- /* 293 */ "exprx ::= ID LP STAR RP",
- /* 294 */ "exprx ::= expr AND expr",
- /* 295 */ "exprx ::= expr OR expr",
- /* 296 */ "exprx ::= expr LT|GT|GE|LE expr",
- /* 297 */ "exprx ::= expr EQ|NE expr",
- /* 298 */ "exprx ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr",
- /* 299 */ "exprx ::= expr PLUS|MINUS expr",
- /* 300 */ "exprx ::= expr STAR|SLASH|REM expr",
- /* 301 */ "exprx ::= expr CONCAT expr",
- /* 302 */ "exprx ::= expr not_opt likeop expr",
- /* 303 */ "exprx ::= expr not_opt likeop expr ESCAPE expr",
- /* 304 */ "exprx ::= expr ISNULL|NOTNULL",
- /* 305 */ "exprx ::= expr NOT NULL",
- /* 306 */ "exprx ::= expr IS not_opt expr",
- /* 307 */ "exprx ::= expr IS NOT DISTINCT FROM expr",
- /* 308 */ "exprx ::= expr IS DISTINCT FROM expr",
- /* 309 */ "exprx ::= NOT expr",
- /* 310 */ "exprx ::= BITNOT expr",
- /* 311 */ "exprx ::= MINUS expr",
- /* 312 */ "exprx ::= PLUS expr",
- /* 313 */ "exprx ::= expr PTR expr",
- /* 314 */ "exprx ::= expr not_opt BETWEEN expr AND expr",
- /* 315 */ "exprx ::= expr not_opt IN LP exprlist RP",
- /* 316 */ "exprx ::= LP select RP",
- /* 317 */ "exprx ::= expr not_opt IN LP select RP",
- /* 318 */ "exprx ::= expr not_opt IN nm dbnm",
- /* 319 */ "exprx ::= EXISTS LP select RP",
- /* 320 */ "exprx ::= CASE case_operand case_exprlist case_else END",
- /* 321 */ "exprx ::= RAISE LP IGNORE RP",
- /* 322 */ "exprx ::= RAISE LP raisetype COMMA nm RP",
- /* 323 */ "exprx ::= ID LP distinct exprlist RP filter_over",
- /* 324 */ "exprx ::= ID LP STAR RP filter_over",
- /* 325 */ "expr ::=",
- /* 326 */ "expr ::= exprx",
- /* 327 */ "not_opt ::=",
- /* 328 */ "not_opt ::= NOT",
- /* 329 */ "likeop ::= LIKE_KW|MATCH",
- /* 330 */ "case_exprlist ::= case_exprlist WHEN expr THEN expr",
- /* 331 */ "case_exprlist ::= WHEN expr THEN expr",
- /* 332 */ "case_else ::= ELSE expr",
- /* 333 */ "case_else ::=",
- /* 334 */ "case_operand ::= exprx",
- /* 335 */ "case_operand ::=",
- /* 336 */ "exprlist ::= nexprlist",
- /* 337 */ "exprlist ::=",
- /* 338 */ "nexprlist ::= nexprlist COMMA expr",
- /* 339 */ "nexprlist ::= exprx",
- /* 340 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt",
- /* 341 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON ID_TAB",
- /* 342 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm DOT ID_IDX_NEW",
- /* 343 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists ID_DB|ID_IDX_NEW",
- /* 344 */ "uniqueflag ::= UNIQUE",
- /* 345 */ "uniqueflag ::=",
- /* 346 */ "idxlist_opt ::=",
- /* 347 */ "idxlist_opt ::= LP idxlist RP",
- /* 348 */ "idxlist ::= idxlist COMMA idxlist_single",
- /* 349 */ "idxlist ::= idxlist_single",
- /* 350 */ "idxlist_single ::= nm collate sortorder",
- /* 351 */ "idxlist_single ::= ID_COL",
- /* 352 */ "collate ::=",
- /* 353 */ "collate ::= COLLATE ids",
- /* 354 */ "collate ::= COLLATE ID_COLLATE",
- /* 355 */ "cmd ::= DROP INDEX ifexists fullname",
- /* 356 */ "cmd ::= DROP INDEX ifexists nm DOT ID_IDX",
- /* 357 */ "cmd ::= DROP INDEX ifexists ID_DB|ID_IDX",
- /* 358 */ "cmd ::= VACUUM vinto",
- /* 359 */ "cmd ::= VACUUM nm vinto",
- /* 360 */ "vinto ::= INTO expr",
- /* 361 */ "vinto ::=",
- /* 362 */ "cmd ::= PRAGMA nm dbnm",
- /* 363 */ "cmd ::= PRAGMA nm dbnm EQ nmnum",
- /* 364 */ "cmd ::= PRAGMA nm dbnm LP nmnum RP",
- /* 365 */ "cmd ::= PRAGMA nm dbnm EQ minus_num",
- /* 366 */ "cmd ::= PRAGMA nm dbnm LP minus_num RP",
- /* 367 */ "cmd ::= PRAGMA nm DOT ID_PRAGMA",
- /* 368 */ "cmd ::= PRAGMA ID_DB|ID_PRAGMA",
- /* 369 */ "nmnum ::= plus_num",
- /* 370 */ "nmnum ::= nm",
- /* 371 */ "nmnum ::= ON",
- /* 372 */ "nmnum ::= DELETE",
- /* 373 */ "nmnum ::= DEFAULT",
- /* 374 */ "plus_num ::= PLUS number",
- /* 375 */ "plus_num ::= number",
- /* 376 */ "minus_num ::= MINUS number",
- /* 377 */ "number ::= INTEGER",
- /* 378 */ "number ::= FLOAT",
- /* 379 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list END",
- /* 380 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause",
- /* 381 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list",
- /* 382 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON ID_TAB",
- /* 383 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm DOT ID_TRIG_NEW",
- /* 384 */ "cmd ::= CREATE temp TRIGGER ifnotexists ID_DB|ID_TRIG_NEW",
- /* 385 */ "trigger_time ::= BEFORE",
- /* 386 */ "trigger_time ::= AFTER",
- /* 387 */ "trigger_time ::= INSTEAD OF",
- /* 388 */ "trigger_time ::=",
- /* 389 */ "trigger_event ::= DELETE",
- /* 390 */ "trigger_event ::= INSERT",
- /* 391 */ "trigger_event ::= UPDATE",
- /* 392 */ "trigger_event ::= UPDATE OF idlist",
- /* 393 */ "foreach_clause ::=",
- /* 394 */ "foreach_clause ::= FOR EACH ROW",
- /* 395 */ "when_clause ::=",
- /* 396 */ "when_clause ::= WHEN expr",
- /* 397 */ "trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI",
- /* 398 */ "trigger_cmd_list ::= trigger_cmd SEMI",
- /* 399 */ "trigger_cmd_list ::= SEMI",
- /* 400 */ "trigger_cmd ::= update_stmt",
- /* 401 */ "trigger_cmd ::= insert_stmt",
- /* 402 */ "trigger_cmd ::= delete_stmt",
- /* 403 */ "trigger_cmd ::= select_stmt",
- /* 404 */ "raisetype ::= ROLLBACK|ABORT|FAIL",
- /* 405 */ "cmd ::= DROP TRIGGER ifexists fullname",
- /* 406 */ "cmd ::= DROP TRIGGER ifexists nm DOT ID_TRIG",
- /* 407 */ "cmd ::= DROP TRIGGER ifexists ID_DB|ID_TRIG",
- /* 408 */ "cmd ::= ATTACH database_kw_opt expr AS expr key_opt",
- /* 409 */ "cmd ::= DETACH database_kw_opt expr",
- /* 410 */ "key_opt ::=",
- /* 411 */ "key_opt ::= KEY expr",
- /* 412 */ "database_kw_opt ::= DATABASE",
- /* 413 */ "database_kw_opt ::=",
- /* 414 */ "cmd ::= REINDEX",
- /* 415 */ "cmd ::= REINDEX nm dbnm",
- /* 416 */ "cmd ::= REINDEX ID_COLLATE",
- /* 417 */ "cmd ::= REINDEX nm DOT ID_TAB|ID_IDX",
- /* 418 */ "cmd ::= REINDEX ID_DB|ID_IDX|ID_TAB",
- /* 419 */ "cmd ::= ANALYZE",
- /* 420 */ "cmd ::= ANALYZE nm dbnm",
- /* 421 */ "cmd ::= ANALYZE nm DOT ID_TAB|ID_IDX",
- /* 422 */ "cmd ::= ANALYZE ID_DB|ID_IDX|ID_TAB",
- /* 423 */ "cmd ::= ALTER TABLE fullname RENAME TO nm",
- /* 424 */ "cmd ::= ALTER TABLE fullname ADD kwcolumn_opt column",
- /* 425 */ "cmd ::= ALTER TABLE fullname DROP kwcolumn_opt nm",
- /* 426 */ "cmd ::= ALTER TABLE fullname RENAME TO ID_TAB_NEW",
- /* 427 */ "cmd ::= ALTER TABLE nm DOT ID_TAB",
- /* 428 */ "cmd ::= ALTER TABLE ID_DB|ID_TAB",
- /* 429 */ "kwcolumn_opt ::=",
- /* 430 */ "kwcolumn_opt ::= COLUMNKW",
- /* 431 */ "cmd ::= create_vtab",
- /* 432 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm",
- /* 433 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm LP vtabarglist RP",
- /* 434 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm DOT ID_TAB_NEW",
- /* 435 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists ID_DB|ID_TAB_NEW",
- /* 436 */ "vtabarglist ::= vtabarg",
- /* 437 */ "vtabarglist ::= vtabarglist COMMA vtabarg",
- /* 438 */ "vtabarg ::=",
- /* 439 */ "vtabarg ::= vtabarg vtabargtoken",
- /* 440 */ "vtabargtoken ::= ANY",
- /* 441 */ "vtabargtoken ::= LP anylist RP",
- /* 442 */ "anylist ::=",
- /* 443 */ "anylist ::= anylist LP anylist RP",
- /* 444 */ "anylist ::= anylist ANY",
- /* 445 */ "with ::=",
- /* 446 */ "with ::= WITH wqlist",
- /* 447 */ "with ::= WITH RECURSIVE wqlist",
- /* 448 */ "wqas ::= AS",
- /* 449 */ "wqas ::= AS MATERIALIZED",
- /* 450 */ "wqas ::= AS NOT MATERIALIZED",
- /* 451 */ "wqlist ::= wqcte",
- /* 452 */ "wqlist ::= wqlist COMMA wqcte",
- /* 453 */ "wqlist ::= ID_TAB_NEW",
- /* 454 */ "wqcte ::= nm idxlist_opt wqas LP select RP",
- /* 455 */ "windowdefn_list ::= windowdefn",
- /* 456 */ "windowdefn_list ::= windowdefn_list COMMA windowdefn",
- /* 457 */ "windowdefn ::= nm AS LP window RP",
- /* 458 */ "window ::= PARTITION BY nexprlist orderby_opt frame_opt",
- /* 459 */ "window ::= nm PARTITION BY nexprlist orderby_opt frame_opt",
- /* 460 */ "window ::= ORDER BY sortlist frame_opt",
- /* 461 */ "window ::= nm ORDER BY sortlist frame_opt",
- /* 462 */ "window ::= frame_opt",
- /* 463 */ "window ::= nm frame_opt",
- /* 464 */ "frame_opt ::=",
- /* 465 */ "frame_opt ::= range_or_rows frame_bound_s frame_exclude_opt",
- /* 466 */ "frame_opt ::= range_or_rows BETWEEN frame_bound_s AND frame_bound_e frame_exclude_opt",
- /* 467 */ "range_or_rows ::= RANGE|ROWS|GROUPS",
- /* 468 */ "frame_bound_s ::= frame_bound",
- /* 469 */ "frame_bound_s ::= UNBOUNDED PRECEDING",
- /* 470 */ "frame_bound_e ::= frame_bound",
- /* 471 */ "frame_bound_e ::= UNBOUNDED FOLLOWING",
- /* 472 */ "frame_bound ::= expr PRECEDING|FOLLOWING",
- /* 473 */ "frame_bound ::= CURRENT ROW",
- /* 474 */ "frame_exclude_opt ::=",
- /* 475 */ "frame_exclude_opt ::= EXCLUDE frame_exclude",
- /* 476 */ "frame_exclude ::= NO OTHERS",
- /* 477 */ "frame_exclude ::= CURRENT ROW",
- /* 478 */ "frame_exclude ::= GROUP",
- /* 479 */ "frame_exclude ::= TIES",
- /* 480 */ "window_clause ::= WINDOW windowdefn_list",
- /* 481 */ "filter_over ::= filter_clause over_clause",
- /* 482 */ "filter_over ::= over_clause",
- /* 483 */ "filter_over ::= filter_clause",
- /* 484 */ "over_clause ::= OVER LP window RP",
- /* 485 */ "over_clause ::= OVER nm",
- /* 486 */ "filter_clause ::= FILTER LP WHERE expr RP",
+ /* 265 */ "insert_stmt ::= with insert_cmd INTO fullname LP idlist rp_opt",
+ /* 266 */ "insert_stmt ::= with insert_cmd INTO",
+ /* 267 */ "insert_stmt ::= with insert_cmd INTO nm DOT",
+ /* 268 */ "insert_stmt ::= with insert_cmd INTO ID_DB|ID_TAB",
+ /* 269 */ "insert_stmt ::= with insert_cmd INTO nm DOT ID_TAB",
+ /* 270 */ "insert_cmd ::= INSERT orconf",
+ /* 271 */ "insert_cmd ::= REPLACE",
+ /* 272 */ "upsert ::=",
+ /* 273 */ "upsert ::= ON CONFLICT LP sortlist RP where_opt DO UPDATE SET setlist where_opt",
+ /* 274 */ "upsert ::= ON CONFLICT LP sortlist RP where_opt DO NOTHING",
+ /* 275 */ "upsert ::= ON CONFLICT DO NOTHING",
+ /* 276 */ "exprx ::= expr not_opt IN ID_DB",
+ /* 277 */ "exprx ::= expr not_opt IN nm DOT ID_TAB",
+ /* 278 */ "exprx ::= ID_DB|ID_TAB|ID_COL|ID_FN",
+ /* 279 */ "exprx ::= tnm DOT ID_TAB|ID_COL",
+ /* 280 */ "exprx ::= tnm DOT nm DOT ID_COL",
+ /* 281 */ "exprx ::= expr COLLATE ID_COLLATE",
+ /* 282 */ "exprx ::= RAISE LP raisetype COMMA ID_ERR_MSG RP",
+ /* 283 */ "exprx ::= CTIME_KW",
+ /* 284 */ "exprx ::= LP nexprlist RP",
+ /* 285 */ "exprx ::= tnm",
+ /* 286 */ "exprx ::= tnm DOT nm",
+ /* 287 */ "exprx ::= tnm DOT",
+ /* 288 */ "exprx ::= tnm DOT nm DOT nm",
+ /* 289 */ "exprx ::= tnm DOT nm DOT",
+ /* 290 */ "exprx ::= VARIABLE",
+ /* 291 */ "exprx ::= expr COLLATE ids",
+ /* 292 */ "exprx ::= CAST LP expr AS typetoken RP",
+ /* 293 */ "exprx ::= ID LP distinct exprlist RP",
+ /* 294 */ "exprx ::= ID LP STAR RP",
+ /* 295 */ "exprx ::= expr AND expr",
+ /* 296 */ "exprx ::= expr OR expr",
+ /* 297 */ "exprx ::= expr LT|GT|GE|LE expr",
+ /* 298 */ "exprx ::= expr EQ|NE expr",
+ /* 299 */ "exprx ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr",
+ /* 300 */ "exprx ::= expr PLUS|MINUS expr",
+ /* 301 */ "exprx ::= expr STAR|SLASH|REM expr",
+ /* 302 */ "exprx ::= expr CONCAT expr",
+ /* 303 */ "exprx ::= expr not_opt likeop expr",
+ /* 304 */ "exprx ::= expr not_opt likeop expr ESCAPE expr",
+ /* 305 */ "exprx ::= expr ISNULL|NOTNULL",
+ /* 306 */ "exprx ::= expr NOT NULL",
+ /* 307 */ "exprx ::= expr IS not_opt expr",
+ /* 308 */ "exprx ::= expr IS NOT DISTINCT FROM expr",
+ /* 309 */ "exprx ::= expr IS DISTINCT FROM expr",
+ /* 310 */ "exprx ::= NOT expr",
+ /* 311 */ "exprx ::= BITNOT expr",
+ /* 312 */ "exprx ::= MINUS expr",
+ /* 313 */ "exprx ::= PLUS expr",
+ /* 314 */ "exprx ::= expr PTR expr",
+ /* 315 */ "exprx ::= expr not_opt BETWEEN expr AND expr",
+ /* 316 */ "exprx ::= expr not_opt IN LP exprlist RP",
+ /* 317 */ "exprx ::= LP select RP",
+ /* 318 */ "exprx ::= expr not_opt IN LP select RP",
+ /* 319 */ "exprx ::= expr not_opt IN nm dbnm",
+ /* 320 */ "exprx ::= EXISTS LP select RP",
+ /* 321 */ "exprx ::= CASE case_operand case_exprlist case_else END",
+ /* 322 */ "exprx ::= RAISE LP IGNORE RP",
+ /* 323 */ "exprx ::= RAISE LP raisetype COMMA nm RP",
+ /* 324 */ "exprx ::= ID LP distinct exprlist RP filter_over",
+ /* 325 */ "exprx ::= ID LP STAR RP filter_over",
+ /* 326 */ "expr ::=",
+ /* 327 */ "expr ::= exprx",
+ /* 328 */ "not_opt ::=",
+ /* 329 */ "not_opt ::= NOT",
+ /* 330 */ "rp_opt ::=",
+ /* 331 */ "rp_opt ::= RP",
+ /* 332 */ "likeop ::= LIKE_KW|MATCH",
+ /* 333 */ "case_exprlist ::= case_exprlist WHEN expr THEN expr",
+ /* 334 */ "case_exprlist ::= WHEN expr THEN expr",
+ /* 335 */ "case_else ::= ELSE expr",
+ /* 336 */ "case_else ::=",
+ /* 337 */ "case_operand ::= exprx",
+ /* 338 */ "case_operand ::=",
+ /* 339 */ "exprlist ::= nexprlist",
+ /* 340 */ "exprlist ::=",
+ /* 341 */ "nexprlist ::= nexprlist COMMA expr",
+ /* 342 */ "nexprlist ::= exprx",
+ /* 343 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt",
+ /* 344 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON ID_TAB",
+ /* 345 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists nm DOT ID_IDX_NEW",
+ /* 346 */ "cmd ::= CREATE uniqueflag INDEX ifnotexists ID_DB|ID_IDX_NEW",
+ /* 347 */ "uniqueflag ::= UNIQUE",
+ /* 348 */ "uniqueflag ::=",
+ /* 349 */ "idxlist_opt ::=",
+ /* 350 */ "idxlist_opt ::= LP idxlist RP",
+ /* 351 */ "idxlist ::= idxlist COMMA idxlist_single",
+ /* 352 */ "idxlist ::= idxlist_single",
+ /* 353 */ "idxlist_single ::= nm collate sortorder",
+ /* 354 */ "idxlist_single ::= ID_COL",
+ /* 355 */ "collate ::=",
+ /* 356 */ "collate ::= COLLATE ids",
+ /* 357 */ "collate ::= COLLATE ID_COLLATE",
+ /* 358 */ "cmd ::= DROP INDEX ifexists fullname",
+ /* 359 */ "cmd ::= DROP INDEX ifexists nm DOT ID_IDX",
+ /* 360 */ "cmd ::= DROP INDEX ifexists ID_DB|ID_IDX",
+ /* 361 */ "cmd ::= VACUUM vinto",
+ /* 362 */ "cmd ::= VACUUM nm vinto",
+ /* 363 */ "vinto ::= INTO expr",
+ /* 364 */ "vinto ::=",
+ /* 365 */ "cmd ::= PRAGMA nm dbnm",
+ /* 366 */ "cmd ::= PRAGMA nm dbnm EQ nmnum",
+ /* 367 */ "cmd ::= PRAGMA nm dbnm LP nmnum RP",
+ /* 368 */ "cmd ::= PRAGMA nm dbnm EQ minus_num",
+ /* 369 */ "cmd ::= PRAGMA nm dbnm LP minus_num RP",
+ /* 370 */ "cmd ::= PRAGMA nm DOT ID_PRAGMA",
+ /* 371 */ "cmd ::= PRAGMA ID_DB|ID_PRAGMA",
+ /* 372 */ "nmnum ::= plus_num",
+ /* 373 */ "nmnum ::= nm",
+ /* 374 */ "nmnum ::= ON",
+ /* 375 */ "nmnum ::= DELETE",
+ /* 376 */ "nmnum ::= DEFAULT",
+ /* 377 */ "plus_num ::= PLUS number",
+ /* 378 */ "plus_num ::= number",
+ /* 379 */ "minus_num ::= MINUS number",
+ /* 380 */ "number ::= INTEGER",
+ /* 381 */ "number ::= FLOAT",
+ /* 382 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list END",
+ /* 383 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause",
+ /* 384 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list",
+ /* 385 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON ID_TAB",
+ /* 386 */ "cmd ::= CREATE temp TRIGGER ifnotexists nm DOT ID_TRIG_NEW",
+ /* 387 */ "cmd ::= CREATE temp TRIGGER ifnotexists ID_DB|ID_TRIG_NEW",
+ /* 388 */ "trigger_time ::= BEFORE",
+ /* 389 */ "trigger_time ::= AFTER",
+ /* 390 */ "trigger_time ::= INSTEAD OF",
+ /* 391 */ "trigger_time ::=",
+ /* 392 */ "trigger_event ::= DELETE",
+ /* 393 */ "trigger_event ::= INSERT",
+ /* 394 */ "trigger_event ::= UPDATE",
+ /* 395 */ "trigger_event ::= UPDATE OF idlist",
+ /* 396 */ "foreach_clause ::=",
+ /* 397 */ "foreach_clause ::= FOR EACH ROW",
+ /* 398 */ "when_clause ::=",
+ /* 399 */ "when_clause ::= WHEN expr",
+ /* 400 */ "trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI",
+ /* 401 */ "trigger_cmd_list ::= trigger_cmd SEMI",
+ /* 402 */ "trigger_cmd_list ::= SEMI",
+ /* 403 */ "trigger_cmd ::= update_stmt",
+ /* 404 */ "trigger_cmd ::= insert_stmt",
+ /* 405 */ "trigger_cmd ::= delete_stmt",
+ /* 406 */ "trigger_cmd ::= select_stmt",
+ /* 407 */ "raisetype ::= ROLLBACK|ABORT|FAIL",
+ /* 408 */ "cmd ::= DROP TRIGGER ifexists fullname",
+ /* 409 */ "cmd ::= DROP TRIGGER ifexists nm DOT ID_TRIG",
+ /* 410 */ "cmd ::= DROP TRIGGER ifexists ID_DB|ID_TRIG",
+ /* 411 */ "cmd ::= ATTACH database_kw_opt expr AS expr key_opt",
+ /* 412 */ "cmd ::= DETACH database_kw_opt expr",
+ /* 413 */ "key_opt ::=",
+ /* 414 */ "key_opt ::= KEY expr",
+ /* 415 */ "database_kw_opt ::= DATABASE",
+ /* 416 */ "database_kw_opt ::=",
+ /* 417 */ "cmd ::= REINDEX",
+ /* 418 */ "cmd ::= REINDEX nm dbnm",
+ /* 419 */ "cmd ::= REINDEX ID_COLLATE",
+ /* 420 */ "cmd ::= REINDEX nm DOT ID_TAB|ID_IDX",
+ /* 421 */ "cmd ::= REINDEX ID_DB|ID_IDX|ID_TAB",
+ /* 422 */ "cmd ::= ANALYZE",
+ /* 423 */ "cmd ::= ANALYZE nm dbnm",
+ /* 424 */ "cmd ::= ANALYZE nm DOT ID_TAB|ID_IDX",
+ /* 425 */ "cmd ::= ANALYZE ID_DB|ID_IDX|ID_TAB",
+ /* 426 */ "cmd ::= ALTER TABLE fullname RENAME TO nm",
+ /* 427 */ "cmd ::= ALTER TABLE fullname ADD kwcolumn_opt column",
+ /* 428 */ "cmd ::= ALTER TABLE fullname DROP kwcolumn_opt nm",
+ /* 429 */ "cmd ::= ALTER TABLE fullname RENAME TO ID_TAB_NEW",
+ /* 430 */ "cmd ::= ALTER TABLE nm DOT ID_TAB",
+ /* 431 */ "cmd ::= ALTER TABLE ID_DB|ID_TAB",
+ /* 432 */ "kwcolumn_opt ::=",
+ /* 433 */ "kwcolumn_opt ::= COLUMNKW",
+ /* 434 */ "cmd ::= create_vtab",
+ /* 435 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm",
+ /* 436 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm LP vtabarglist RP",
+ /* 437 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm DOT ID_TAB_NEW",
+ /* 438 */ "create_vtab ::= CREATE VIRTUAL TABLE ifnotexists ID_DB|ID_TAB_NEW",
+ /* 439 */ "vtabarglist ::= vtabarg",
+ /* 440 */ "vtabarglist ::= vtabarglist COMMA vtabarg",
+ /* 441 */ "vtabarg ::=",
+ /* 442 */ "vtabarg ::= vtabarg vtabargtoken",
+ /* 443 */ "vtabargtoken ::= ANY",
+ /* 444 */ "vtabargtoken ::= LP anylist RP",
+ /* 445 */ "anylist ::=",
+ /* 446 */ "anylist ::= anylist LP anylist RP",
+ /* 447 */ "anylist ::= anylist ANY",
+ /* 448 */ "with ::=",
+ /* 449 */ "with ::= WITH wqlist",
+ /* 450 */ "with ::= WITH RECURSIVE wqlist",
+ /* 451 */ "wqas ::= AS",
+ /* 452 */ "wqas ::= AS MATERIALIZED",
+ /* 453 */ "wqas ::= AS NOT MATERIALIZED",
+ /* 454 */ "wqlist ::= wqcte",
+ /* 455 */ "wqlist ::= wqlist COMMA wqcte",
+ /* 456 */ "wqlist ::= ID_TAB_NEW",
+ /* 457 */ "wqcte ::= nm idxlist_opt wqas LP select RP",
+ /* 458 */ "windowdefn_list ::= windowdefn",
+ /* 459 */ "windowdefn_list ::= windowdefn_list COMMA windowdefn",
+ /* 460 */ "windowdefn ::= nm AS LP window RP",
+ /* 461 */ "window ::= PARTITION BY nexprlist orderby_opt frame_opt",
+ /* 462 */ "window ::= nm PARTITION BY nexprlist orderby_opt frame_opt",
+ /* 463 */ "window ::= ORDER BY sortlist frame_opt",
+ /* 464 */ "window ::= nm ORDER BY sortlist frame_opt",
+ /* 465 */ "window ::= frame_opt",
+ /* 466 */ "window ::= nm frame_opt",
+ /* 467 */ "frame_opt ::=",
+ /* 468 */ "frame_opt ::= range_or_rows frame_bound_s frame_exclude_opt",
+ /* 469 */ "frame_opt ::= range_or_rows BETWEEN frame_bound_s AND frame_bound_e frame_exclude_opt",
+ /* 470 */ "range_or_rows ::= RANGE|ROWS|GROUPS",
+ /* 471 */ "frame_bound_s ::= frame_bound",
+ /* 472 */ "frame_bound_s ::= UNBOUNDED PRECEDING",
+ /* 473 */ "frame_bound_e ::= frame_bound",
+ /* 474 */ "frame_bound_e ::= UNBOUNDED FOLLOWING",
+ /* 475 */ "frame_bound ::= expr PRECEDING|FOLLOWING",
+ /* 476 */ "frame_bound ::= CURRENT ROW",
+ /* 477 */ "frame_exclude_opt ::=",
+ /* 478 */ "frame_exclude_opt ::= EXCLUDE frame_exclude",
+ /* 479 */ "frame_exclude ::= NO OTHERS",
+ /* 480 */ "frame_exclude ::= CURRENT ROW",
+ /* 481 */ "frame_exclude ::= GROUP",
+ /* 482 */ "frame_exclude ::= TIES",
+ /* 483 */ "window_clause ::= WINDOW windowdefn_list",
+ /* 484 */ "filter_over ::= filter_clause over_clause",
+ /* 485 */ "filter_over ::= over_clause",
+ /* 486 */ "filter_over ::= filter_clause",
+ /* 487 */ "over_clause ::= OVER LP window RP",
+ /* 488 */ "over_clause ::= OVER nm",
+ /* 489 */ "filter_clause ::= FILTER LP WHERE expr RP",
};
#endif /* NDEBUG */
@@ -1945,21 +1945,21 @@ static void yy_destructor(
case 277: /* delete_stmt */
case 279: /* update_stmt */
case 282: /* insert_stmt */
- case 303: /* trigger_cmd */
- case 307: /* create_vtab */
+ case 304: /* trigger_cmd */
+ case 308: /* create_vtab */
{
-parser_safe_delete((yypminor->yy41));
+parser_safe_delete((yypminor->yy635));
}
break;
case 199: /* explain */
{
-parser_safe_delete((yypminor->yy499));
+parser_safe_delete((yypminor->yy571));
}
break;
case 201: /* transtype */
case 202: /* trans_opt */
{
-parser_safe_delete((yypminor->yy512));
+parser_safe_delete((yypminor->yy100));
}
break;
case 203: /* nm */
@@ -1969,12 +1969,12 @@ parser_safe_delete((yypminor->yy512));
case 219: /* ids */
case 221: /* typename */
case 272: /* dbnm */
- case 294: /* collate */
- case 309: /* vtabarg */
- case 310: /* vtabargtoken */
- case 311: /* anylist */
+ case 295: /* collate */
+ case 310: /* vtabarg */
+ case 311: /* vtabargtoken */
+ case 312: /* anylist */
{
-parser_safe_delete((yypminor->yy319));
+parser_safe_delete((yypminor->yy255));
}
break;
case 204: /* savepoint_opt */
@@ -1983,354 +1983,355 @@ parser_safe_delete((yypminor->yy319));
case 234: /* gen_always */
case 240: /* tconscomma */
case 247: /* ifexists */
- case 286: /* not_opt */
- case 292: /* uniqueflag */
- case 304: /* database_kw_opt */
- case 306: /* kwcolumn_opt */
+ case 285: /* rp_opt */
+ case 287: /* not_opt */
+ case 293: /* uniqueflag */
+ case 305: /* database_kw_opt */
+ case 307: /* kwcolumn_opt */
{
-parser_safe_delete((yypminor->yy225));
+parser_safe_delete((yypminor->yy35));
}
break;
case 205: /* temp */
case 254: /* distinct */
{
-parser_safe_delete((yypminor->yy130));
+parser_safe_delete((yypminor->yy562));
}
break;
case 207: /* fullname */
{
-parser_safe_delete((yypminor->yy396));
+parser_safe_delete((yypminor->yy520));
}
break;
case 208: /* columnlist */
{
-parser_safe_delete((yypminor->yy390));
+parser_safe_delete((yypminor->yy234));
}
break;
case 209: /* conslist_opt */
case 239: /* conslist */
{
-parser_safe_delete((yypminor->yy115));
+parser_safe_delete((yypminor->yy445));
}
break;
case 210: /* table_options */
{
-parser_safe_delete((yypminor->yy455));
+parser_safe_delete((yypminor->yy217));
}
break;
case 211: /* select */
case 250: /* selectnowith */
{
-parser_safe_delete((yypminor->yy297));
+parser_safe_delete((yypminor->yy73));
}
break;
case 212: /* table_option */
{
-parser_safe_delete((yypminor->yy629));
+parser_safe_delete((yypminor->yy607));
}
break;
case 213: /* column */
{
-parser_safe_delete((yypminor->yy3));
+parser_safe_delete((yypminor->yy115));
}
break;
case 215: /* type */
case 220: /* typetoken */
{
-parser_safe_delete((yypminor->yy267));
+parser_safe_delete((yypminor->yy601));
}
break;
case 216: /* carglist */
{
-parser_safe_delete((yypminor->yy323));
+parser_safe_delete((yypminor->yy259));
}
break;
case 222: /* signed */
case 223: /* plus_num */
case 224: /* minus_num */
case 226: /* term */
- case 296: /* nmnum */
- case 297: /* number */
+ case 297: /* nmnum */
+ case 298: /* number */
{
-parser_safe_delete((yypminor->yy393));
+parser_safe_delete((yypminor->yy629));
}
break;
case 225: /* ccons */
{
-parser_safe_delete((yypminor->yy448));
+parser_safe_delete((yypminor->yy64));
}
break;
case 227: /* expr */
case 257: /* where_opt */
case 259: /* having_opt */
- case 285: /* exprx */
- case 288: /* case_operand */
- case 290: /* case_else */
- case 295: /* vinto */
- case 301: /* when_clause */
- case 305: /* key_opt */
-{
-parser_safe_delete((yypminor->yy186));
+ case 286: /* exprx */
+ case 289: /* case_operand */
+ case 291: /* case_else */
+ case 296: /* vinto */
+ case 302: /* when_clause */
+ case 306: /* key_opt */
+{
+parser_safe_delete((yypminor->yy176));
}
break;
case 228: /* onconf */
case 244: /* resolvetype */
case 245: /* orconf */
{
-parser_safe_delete((yypminor->yy136));
+parser_safe_delete((yypminor->yy66));
}
break;
case 229: /* sortorder */
{
-parser_safe_delete((yypminor->yy35));
+parser_safe_delete((yypminor->yy645));
}
break;
case 231: /* idxlist_opt */
case 242: /* idxlist */
{
-parser_safe_delete((yypminor->yy627));
+parser_safe_delete((yypminor->yy527));
}
break;
case 232: /* refargs */
{
-parser_safe_delete((yypminor->yy156));
+parser_safe_delete((yypminor->yy56));
}
break;
case 233: /* defer_subclause */
case 243: /* defer_subclause_opt */
{
-parser_safe_delete((yypminor->yy53));
+parser_safe_delete((yypminor->yy218));
}
break;
case 235: /* tnm */
{
-parser_safe_delete((yypminor->yy380));
+parser_safe_delete((yypminor->yy542));
}
break;
case 236: /* refarg */
{
-parser_safe_delete((yypminor->yy205));
+parser_safe_delete((yypminor->yy587));
}
break;
case 237: /* refact */
{
-parser_safe_delete((yypminor->yy106));
+parser_safe_delete((yypminor->yy488));
}
break;
case 238: /* init_deferred_pred_opt */
{
-parser_safe_delete((yypminor->yy612));
+parser_safe_delete((yypminor->yy536));
}
break;
case 241: /* tcons */
{
-parser_safe_delete((yypminor->yy400));
+parser_safe_delete((yypminor->yy166));
}
break;
case 249: /* with */
{
-parser_safe_delete((yypminor->yy161));
+parser_safe_delete((yypminor->yy321));
}
break;
case 251: /* oneselect */
{
-parser_safe_delete((yypminor->yy378));
+parser_safe_delete((yypminor->yy438));
}
break;
case 252: /* multiselect_op */
{
-parser_safe_delete((yypminor->yy142));
+parser_safe_delete((yypminor->yy574));
}
break;
case 253: /* values */
{
-parser_safe_delete((yypminor->yy522));
+parser_safe_delete((yypminor->yy54));
}
break;
case 255: /* selcollist */
case 265: /* sclp */
case 278: /* returning */
{
-parser_safe_delete((yypminor->yy27));
+parser_safe_delete((yypminor->yy421));
}
break;
case 256: /* from */
case 267: /* joinsrc */
{
-parser_safe_delete((yypminor->yy553));
+parser_safe_delete((yypminor->yy335));
}
break;
case 258: /* groupby_opt */
case 263: /* nexprlist */
case 264: /* exprlist */
- case 289: /* case_exprlist */
+ case 290: /* case_exprlist */
{
-parser_safe_delete((yypminor->yy615));
+parser_safe_delete((yypminor->yy567));
}
break;
case 260: /* orderby_opt */
case 275: /* sortlist */
{
-parser_safe_delete((yypminor->yy226));
+parser_safe_delete((yypminor->yy499));
}
break;
case 261: /* limit_opt */
{
-parser_safe_delete((yypminor->yy360));
+parser_safe_delete((yypminor->yy4));
}
break;
case 262: /* window_clause */
- case 315: /* windowdefn_list */
+ case 316: /* windowdefn_list */
{
-parser_safe_delete((yypminor->yy525));
+parser_safe_delete((yypminor->yy555));
}
break;
case 266: /* as */
{
-parser_safe_delete((yypminor->yy628));
+parser_safe_delete((yypminor->yy280));
}
break;
case 268: /* singlesrc */
{
-parser_safe_delete((yypminor->yy595));
+parser_safe_delete((yypminor->yy393));
}
break;
case 269: /* seltablist */
{
-parser_safe_delete((yypminor->yy107));
+parser_safe_delete((yypminor->yy195));
}
break;
case 270: /* joinop */
{
-parser_safe_delete((yypminor->yy449));
+parser_safe_delete((yypminor->yy461));
}
break;
case 271: /* joinconstr_opt */
{
-parser_safe_delete((yypminor->yy215));
+parser_safe_delete((yypminor->yy423));
}
break;
case 273: /* indexed_opt */
{
-parser_safe_delete((yypminor->yy300));
+parser_safe_delete((yypminor->yy224));
}
break;
case 274: /* idlist */
case 281: /* idlist_opt */
- case 308: /* vtabarglist */
+ case 309: /* vtabarglist */
{
-parser_safe_delete((yypminor->yy173));
+parser_safe_delete((yypminor->yy336));
}
break;
case 276: /* nulls */
{
-parser_safe_delete((yypminor->yy315));
+parser_safe_delete((yypminor->yy99));
}
break;
case 280: /* setlist */
{
-parser_safe_delete((yypminor->yy621));
+parser_safe_delete((yypminor->yy617));
}
break;
case 283: /* insert_cmd */
{
-parser_safe_delete((yypminor->yy308));
+parser_safe_delete((yypminor->yy281));
}
break;
case 284: /* upsert */
{
-parser_safe_delete((yypminor->yy332));
+parser_safe_delete((yypminor->yy16));
}
break;
- case 287: /* likeop */
+ case 288: /* likeop */
{
-parser_safe_delete((yypminor->yy274));
+parser_safe_delete((yypminor->yy104));
}
break;
- case 291: /* filter_over */
+ case 292: /* filter_over */
{
-parser_safe_delete((yypminor->yy181));
+parser_safe_delete((yypminor->yy487));
}
break;
- case 293: /* idxlist_single */
+ case 294: /* idxlist_single */
{
-parser_safe_delete((yypminor->yy110));
+parser_safe_delete((yypminor->yy540));
}
break;
- case 298: /* trigger_time */
+ case 299: /* trigger_time */
{
-parser_safe_delete((yypminor->yy120));
+parser_safe_delete((yypminor->yy612));
}
break;
- case 299: /* trigger_event */
+ case 300: /* trigger_event */
{
-parser_safe_delete((yypminor->yy259));
+parser_safe_delete((yypminor->yy407));
}
break;
- case 300: /* foreach_clause */
+ case 301: /* foreach_clause */
{
-parser_safe_delete((yypminor->yy456));
+parser_safe_delete((yypminor->yy403));
}
break;
- case 302: /* trigger_cmd_list */
+ case 303: /* trigger_cmd_list */
{
-parser_safe_delete((yypminor->yy240));
+parser_safe_delete((yypminor->yy575));
}
break;
- case 312: /* wqlist */
+ case 313: /* wqlist */
{
-parser_safe_delete((yypminor->yy164));
+parser_safe_delete((yypminor->yy17));
}
break;
- case 313: /* wqas */
+ case 314: /* wqas */
{
-parser_safe_delete((yypminor->yy21));
+parser_safe_delete((yypminor->yy383));
}
break;
- case 314: /* wqcte */
+ case 315: /* wqcte */
{
-parser_safe_delete((yypminor->yy146));
+parser_safe_delete((yypminor->yy366));
}
break;
- case 316: /* windowdefn */
+ case 317: /* windowdefn */
{
-parser_safe_delete((yypminor->yy562));
+parser_safe_delete((yypminor->yy74));
}
break;
- case 317: /* window */
+ case 318: /* window */
{
-parser_safe_delete((yypminor->yy162));
+parser_safe_delete((yypminor->yy14));
}
break;
- case 318: /* frame_opt */
+ case 319: /* frame_opt */
{
-parser_safe_delete((yypminor->yy149));
+parser_safe_delete((yypminor->yy585));
}
break;
- case 319: /* range_or_rows */
+ case 320: /* range_or_rows */
{
-parser_safe_delete((yypminor->yy143));
+parser_safe_delete((yypminor->yy34));
}
break;
- case 320: /* frame_bound_s */
- case 322: /* frame_bound_e */
+ case 321: /* frame_bound_s */
+ case 323: /* frame_bound_e */
{
-parser_safe_delete((yypminor->yy285));
+parser_safe_delete((yypminor->yy394));
}
break;
- case 323: /* frame_bound */
+ case 324: /* frame_bound */
{
-parser_safe_delete((yypminor->yy285));parser_safe_delete((yypminor->yy285));parser_safe_delete((yypminor->yy285));
+parser_safe_delete((yypminor->yy394));parser_safe_delete((yypminor->yy394));parser_safe_delete((yypminor->yy394));
}
break;
- case 325: /* filter_clause */
+ case 326: /* filter_clause */
{
-parser_safe_delete((yypminor->yy39));
+parser_safe_delete((yypminor->yy269));
}
break;
- case 326: /* over_clause */
+ case 327: /* over_clause */
{
-parser_safe_delete((yypminor->yy11));
+parser_safe_delete((yypminor->yy231));
}
break;
default: break; /* If no destructor action specified: do nothing */
@@ -2846,6 +2847,7 @@ static const struct {
{ 195, 1 },
{ 282, 8 },
{ 282, 8 },
+ { 282, 7 },
{ 282, 3 },
{ 282, 5 },
{ 282, 4 },
@@ -2856,67 +2858,69 @@ static const struct {
{ 284, 11 },
{ 284, 8 },
{ 284, 4 },
- { 285, 4 },
- { 285, 6 },
- { 285, 1 },
- { 285, 3 },
- { 285, 5 },
- { 285, 3 },
- { 285, 6 },
- { 285, 1 },
- { 285, 3 },
- { 285, 1 },
- { 285, 3 },
- { 285, 2 },
- { 285, 5 },
- { 285, 4 },
- { 285, 1 },
- { 285, 3 },
- { 285, 6 },
- { 285, 5 },
- { 285, 4 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 3 },
- { 285, 4 },
- { 285, 6 },
- { 285, 2 },
- { 285, 3 },
- { 285, 4 },
- { 285, 6 },
- { 285, 5 },
- { 285, 2 },
- { 285, 2 },
- { 285, 2 },
- { 285, 2 },
- { 285, 3 },
- { 285, 6 },
- { 285, 6 },
- { 285, 3 },
- { 285, 6 },
- { 285, 5 },
- { 285, 4 },
- { 285, 5 },
- { 285, 4 },
- { 285, 6 },
- { 285, 6 },
- { 285, 5 },
+ { 286, 4 },
+ { 286, 6 },
+ { 286, 1 },
+ { 286, 3 },
+ { 286, 5 },
+ { 286, 3 },
+ { 286, 6 },
+ { 286, 1 },
+ { 286, 3 },
+ { 286, 1 },
+ { 286, 3 },
+ { 286, 2 },
+ { 286, 5 },
+ { 286, 4 },
+ { 286, 1 },
+ { 286, 3 },
+ { 286, 6 },
+ { 286, 5 },
+ { 286, 4 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 3 },
+ { 286, 4 },
+ { 286, 6 },
+ { 286, 2 },
+ { 286, 3 },
+ { 286, 4 },
+ { 286, 6 },
+ { 286, 5 },
+ { 286, 2 },
+ { 286, 2 },
+ { 286, 2 },
+ { 286, 2 },
+ { 286, 3 },
+ { 286, 6 },
+ { 286, 6 },
+ { 286, 3 },
+ { 286, 6 },
+ { 286, 5 },
+ { 286, 4 },
+ { 286, 5 },
+ { 286, 4 },
+ { 286, 6 },
+ { 286, 6 },
+ { 286, 5 },
{ 227, 0 },
{ 227, 1 },
- { 286, 0 },
- { 286, 1 },
+ { 287, 0 },
{ 287, 1 },
- { 289, 5 },
- { 289, 4 },
- { 290, 2 },
- { 290, 0 },
+ { 285, 0 },
+ { 285, 1 },
{ 288, 1 },
- { 288, 0 },
+ { 290, 5 },
+ { 290, 4 },
+ { 291, 2 },
+ { 291, 0 },
+ { 289, 1 },
+ { 289, 0 },
{ 264, 1 },
{ 264, 0 },
{ 263, 3 },
@@ -2925,24 +2929,24 @@ static const struct {
{ 195, 8 },
{ 195, 7 },
{ 195, 5 },
- { 292, 1 },
- { 292, 0 },
+ { 293, 1 },
+ { 293, 0 },
{ 231, 0 },
{ 231, 3 },
{ 242, 3 },
{ 242, 1 },
- { 293, 3 },
- { 293, 1 },
- { 294, 0 },
- { 294, 2 },
- { 294, 2 },
+ { 294, 3 },
+ { 294, 1 },
+ { 295, 0 },
+ { 295, 2 },
+ { 295, 2 },
{ 195, 4 },
{ 195, 6 },
{ 195, 4 },
{ 195, 2 },
{ 195, 3 },
- { 295, 2 },
- { 295, 0 },
+ { 296, 2 },
+ { 296, 0 },
{ 195, 3 },
{ 195, 5 },
{ 195, 6 },
@@ -2950,51 +2954,51 @@ static const struct {
{ 195, 6 },
{ 195, 4 },
{ 195, 2 },
- { 296, 1 },
- { 296, 1 },
- { 296, 1 },
- { 296, 1 },
- { 296, 1 },
+ { 297, 1 },
+ { 297, 1 },
+ { 297, 1 },
+ { 297, 1 },
+ { 297, 1 },
{ 223, 2 },
{ 223, 1 },
{ 224, 2 },
- { 297, 1 },
- { 297, 1 },
+ { 298, 1 },
+ { 298, 1 },
{ 195, 15 },
{ 195, 12 },
{ 195, 14 },
{ 195, 10 },
{ 195, 7 },
{ 195, 5 },
- { 298, 1 },
- { 298, 1 },
- { 298, 2 },
- { 298, 0 },
{ 299, 1 },
{ 299, 1 },
- { 299, 1 },
- { 299, 3 },
- { 300, 0 },
+ { 299, 2 },
+ { 299, 0 },
+ { 300, 1 },
+ { 300, 1 },
+ { 300, 1 },
{ 300, 3 },
{ 301, 0 },
- { 301, 2 },
- { 302, 3 },
+ { 301, 3 },
+ { 302, 0 },
{ 302, 2 },
- { 302, 1 },
- { 303, 1 },
- { 303, 1 },
- { 303, 1 },
+ { 303, 3 },
+ { 303, 2 },
{ 303, 1 },
+ { 304, 1 },
+ { 304, 1 },
+ { 304, 1 },
+ { 304, 1 },
{ 246, 1 },
{ 195, 4 },
{ 195, 6 },
{ 195, 4 },
{ 195, 6 },
{ 195, 3 },
+ { 306, 0 },
+ { 306, 2 },
+ { 305, 1 },
{ 305, 0 },
- { 305, 2 },
- { 304, 1 },
- { 304, 0 },
{ 195, 1 },
{ 195, 3 },
{ 195, 2 },
@@ -3010,64 +3014,64 @@ static const struct {
{ 195, 6 },
{ 195, 5 },
{ 195, 3 },
- { 306, 0 },
- { 306, 1 },
+ { 307, 0 },
+ { 307, 1 },
{ 195, 1 },
- { 307, 8 },
- { 307, 11 },
- { 307, 7 },
- { 307, 5 },
- { 308, 1 },
- { 308, 3 },
- { 309, 0 },
- { 309, 2 },
- { 310, 1 },
- { 310, 3 },
- { 311, 0 },
- { 311, 4 },
- { 311, 2 },
+ { 308, 8 },
+ { 308, 11 },
+ { 308, 7 },
+ { 308, 5 },
+ { 309, 1 },
+ { 309, 3 },
+ { 310, 0 },
+ { 310, 2 },
+ { 311, 1 },
+ { 311, 3 },
+ { 312, 0 },
+ { 312, 4 },
+ { 312, 2 },
{ 249, 0 },
{ 249, 2 },
{ 249, 3 },
+ { 314, 1 },
+ { 314, 2 },
+ { 314, 3 },
{ 313, 1 },
- { 313, 2 },
{ 313, 3 },
- { 312, 1 },
- { 312, 3 },
- { 312, 1 },
- { 314, 6 },
- { 315, 1 },
- { 315, 3 },
- { 316, 5 },
- { 317, 5 },
- { 317, 6 },
- { 317, 4 },
+ { 313, 1 },
+ { 315, 6 },
+ { 316, 1 },
+ { 316, 3 },
{ 317, 5 },
- { 317, 1 },
- { 317, 2 },
- { 318, 0 },
- { 318, 3 },
+ { 318, 5 },
{ 318, 6 },
- { 319, 1 },
+ { 318, 4 },
+ { 318, 5 },
+ { 318, 1 },
+ { 318, 2 },
+ { 319, 0 },
+ { 319, 3 },
+ { 319, 6 },
{ 320, 1 },
- { 320, 2 },
- { 322, 1 },
- { 322, 2 },
- { 323, 2 },
- { 323, 2 },
- { 321, 0 },
+ { 321, 1 },
{ 321, 2 },
+ { 323, 1 },
+ { 323, 2 },
{ 324, 2 },
{ 324, 2 },
- { 324, 1 },
- { 324, 1 },
+ { 322, 0 },
+ { 322, 2 },
+ { 325, 2 },
+ { 325, 2 },
+ { 325, 1 },
+ { 325, 1 },
{ 262, 2 },
- { 291, 2 },
- { 291, 1 },
- { 291, 1 },
- { 326, 4 },
- { 326, 2 },
- { 325, 5 },
+ { 292, 2 },
+ { 292, 1 },
+ { 292, 1 },
+ { 327, 4 },
+ { 327, 2 },
+ { 326, 5 },
};
static void yy_accept(yyParser*); /* Forward Declaration */
@@ -3127,119 +3131,119 @@ static void yy_reduce(
** break;
*/
case 1: /* cmdlist ::= cmdlist ecmd */
-{parserContext->addQuery(yymsp[0].minor.yy41); DONT_INHERIT_TOKENS("cmdlist");}
+{parserContext->addQuery(yymsp[0].minor.yy635); DONT_INHERIT_TOKENS("cmdlist");}
break;
case 2: /* cmdlist ::= ecmd */
-{parserContext->addQuery(yymsp[0].minor.yy41);}
+{parserContext->addQuery(yymsp[0].minor.yy635);}
break;
case 3: /* ecmd ::= SEMI */
-{yygotominor.yy41 = new SqliteEmptyQuery();}
+{yygotominor.yy635 = new SqliteEmptyQuery();}
break;
case 4: /* ecmd ::= explain cmdx SEMI */
{
- yygotominor.yy41 = yymsp[-1].minor.yy41;
- yygotominor.yy41->explain = yymsp[-2].minor.yy499->explain;
- yygotominor.yy41->queryPlan = yymsp[-2].minor.yy499->queryPlan;
- delete yymsp[-2].minor.yy499;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = yymsp[-1].minor.yy635;
+ yygotominor.yy635->explain = yymsp[-2].minor.yy571->explain;
+ yygotominor.yy635->queryPlan = yymsp[-2].minor.yy571->queryPlan;
+ delete yymsp[-2].minor.yy571;
+ objectForTokens = yygotominor.yy635;
}
break;
case 5: /* explain ::= */
-{yygotominor.yy499 = new ParserStubExplain(false, false);}
+{yygotominor.yy571 = new ParserStubExplain(false, false);}
break;
case 6: /* explain ::= EXPLAIN */
-{yygotominor.yy499 = new ParserStubExplain(true, false);}
+{yygotominor.yy571 = new ParserStubExplain(true, false);}
break;
case 7: /* explain ::= EXPLAIN QUERY PLAN */
-{yygotominor.yy499 = new ParserStubExplain(true, true);}
+{yygotominor.yy571 = new ParserStubExplain(true, true);}
break;
case 8: /* cmdx ::= cmd */
- case 400: /* trigger_cmd ::= update_stmt */ yytestcase(yyruleno==400);
- case 401: /* trigger_cmd ::= insert_stmt */ yytestcase(yyruleno==401);
- case 402: /* trigger_cmd ::= delete_stmt */ yytestcase(yyruleno==402);
- case 403: /* trigger_cmd ::= select_stmt */ yytestcase(yyruleno==403);
- case 431: /* cmd ::= create_vtab */ yytestcase(yyruleno==431);
-{yygotominor.yy41 = yymsp[0].minor.yy41;}
+ case 403: /* trigger_cmd ::= update_stmt */ yytestcase(yyruleno==403);
+ case 404: /* trigger_cmd ::= insert_stmt */ yytestcase(yyruleno==404);
+ case 405: /* trigger_cmd ::= delete_stmt */ yytestcase(yyruleno==405);
+ case 406: /* trigger_cmd ::= select_stmt */ yytestcase(yyruleno==406);
+ case 434: /* cmd ::= create_vtab */ yytestcase(yyruleno==434);
+{yygotominor.yy635 = yymsp[0].minor.yy635;}
break;
case 9: /* cmd ::= BEGIN transtype trans_opt */
{
- yygotominor.yy41 = new SqliteBeginTrans(
- yymsp[-1].minor.yy512->type,
- yymsp[0].minor.yy512->transactionKw,
- yymsp[0].minor.yy512->name
+ yygotominor.yy635 = new SqliteBeginTrans(
+ yymsp[-1].minor.yy100->type,
+ yymsp[0].minor.yy100->transactionKw,
+ yymsp[0].minor.yy100->name
);
- delete yymsp[0].minor.yy512;
- delete yymsp[-1].minor.yy512;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[0].minor.yy100;
+ delete yymsp[-1].minor.yy100;
+ objectForTokens = yygotominor.yy635;
}
break;
case 10: /* trans_opt ::= */
case 14: /* transtype ::= */ yytestcase(yyruleno==14);
-{yygotominor.yy512 = new ParserStubTransDetails();}
+{yygotominor.yy100 = new ParserStubTransDetails();}
break;
case 11: /* trans_opt ::= TRANSACTION */
{
- yygotominor.yy512 = new ParserStubTransDetails();
- yygotominor.yy512->transactionKw = true;
+ yygotominor.yy100 = new ParserStubTransDetails();
+ yygotominor.yy100->transactionKw = true;
}
break;
case 12: /* trans_opt ::= TRANSACTION nm */
case 13: /* trans_opt ::= TRANSACTION ID_TRANS */ yytestcase(yyruleno==13);
{
- yygotominor.yy512 = new ParserStubTransDetails();
- yygotominor.yy512->transactionKw = true;
- yygotominor.yy512->name = *(yymsp[0].minor.yy319);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy100 = new ParserStubTransDetails();
+ yygotominor.yy100->transactionKw = true;
+ yygotominor.yy100->name = *(yymsp[0].minor.yy255);
+ delete yymsp[0].minor.yy255;
}
break;
case 15: /* transtype ::= DEFERRED */
{
- yygotominor.yy512 = new ParserStubTransDetails();
- yygotominor.yy512->type = SqliteBeginTrans::Type::DEFERRED;
+ yygotominor.yy100 = new ParserStubTransDetails();
+ yygotominor.yy100->type = SqliteBeginTrans::Type::DEFERRED;
}
break;
case 16: /* transtype ::= IMMEDIATE */
{
- yygotominor.yy512 = new ParserStubTransDetails();
- yygotominor.yy512->type = SqliteBeginTrans::Type::IMMEDIATE;
+ yygotominor.yy100 = new ParserStubTransDetails();
+ yygotominor.yy100->type = SqliteBeginTrans::Type::IMMEDIATE;
}
break;
case 17: /* transtype ::= EXCLUSIVE */
{
- yygotominor.yy512 = new ParserStubTransDetails();
- yygotominor.yy512->type = SqliteBeginTrans::Type::EXCLUSIVE;
+ yygotominor.yy100 = new ParserStubTransDetails();
+ yygotominor.yy100->type = SqliteBeginTrans::Type::EXCLUSIVE;
}
break;
case 18: /* cmd ::= COMMIT trans_opt */
{
- yygotominor.yy41 = new SqliteCommitTrans(
- yymsp[0].minor.yy512->transactionKw,
- yymsp[0].minor.yy512->name,
+ yygotominor.yy635 = new SqliteCommitTrans(
+ yymsp[0].minor.yy100->transactionKw,
+ yymsp[0].minor.yy100->name,
false
);
- delete yymsp[0].minor.yy512;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[0].minor.yy100;
+ objectForTokens = yygotominor.yy635;
}
break;
case 19: /* cmd ::= END trans_opt */
{
- yygotominor.yy41 = new SqliteCommitTrans(
- yymsp[0].minor.yy512->transactionKw,
- yymsp[0].minor.yy512->name,
+ yygotominor.yy635 = new SqliteCommitTrans(
+ yymsp[0].minor.yy100->transactionKw,
+ yymsp[0].minor.yy100->name,
true
);
- delete yymsp[0].minor.yy512;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[0].minor.yy100;
+ objectForTokens = yygotominor.yy635;
}
break;
case 20: /* cmd ::= ROLLBACK trans_opt */
{
- yygotominor.yy41 = new SqliteRollback(
- yymsp[0].minor.yy512->transactionKw,
- yymsp[0].minor.yy512->name
+ yygotominor.yy635 = new SqliteRollback(
+ yymsp[0].minor.yy100->transactionKw,
+ yymsp[0].minor.yy100->name
);
- delete yymsp[0].minor.yy512;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[0].minor.yy100;
+ objectForTokens = yygotominor.yy635;
}
break;
case 21: /* savepoint_opt ::= SAVEPOINT */
@@ -3248,11 +3252,12 @@ static void yy_reduce(
case 97: /* autoinc ::= AUTOINCR */ yytestcase(yyruleno==97);
case 119: /* tconscomma ::= COMMA */ yytestcase(yyruleno==119);
case 141: /* ifexists ::= IF EXISTS */ yytestcase(yyruleno==141);
- case 328: /* not_opt ::= NOT */ yytestcase(yyruleno==328);
- case 344: /* uniqueflag ::= UNIQUE */ yytestcase(yyruleno==344);
- case 412: /* database_kw_opt ::= DATABASE */ yytestcase(yyruleno==412);
- case 429: /* kwcolumn_opt ::= */ yytestcase(yyruleno==429);
-{yygotominor.yy225 = new bool(true);}
+ case 329: /* not_opt ::= NOT */ yytestcase(yyruleno==329);
+ case 331: /* rp_opt ::= RP */ yytestcase(yyruleno==331);
+ case 347: /* uniqueflag ::= UNIQUE */ yytestcase(yyruleno==347);
+ case 415: /* database_kw_opt ::= DATABASE */ yytestcase(yyruleno==415);
+ case 432: /* kwcolumn_opt ::= */ yytestcase(yyruleno==432);
+{yygotominor.yy35 = new bool(true);}
break;
case 22: /* savepoint_opt ::= */
case 40: /* ifnotexists ::= */ yytestcase(yyruleno==40);
@@ -3260,37 +3265,38 @@ static void yy_reduce(
case 96: /* autoinc ::= */ yytestcase(yyruleno==96);
case 120: /* tconscomma ::= */ yytestcase(yyruleno==120);
case 142: /* ifexists ::= */ yytestcase(yyruleno==142);
- case 327: /* not_opt ::= */ yytestcase(yyruleno==327);
- case 345: /* uniqueflag ::= */ yytestcase(yyruleno==345);
- case 413: /* database_kw_opt ::= */ yytestcase(yyruleno==413);
- case 430: /* kwcolumn_opt ::= COLUMNKW */ yytestcase(yyruleno==430);
-{yygotominor.yy225 = new bool(false);}
+ case 328: /* not_opt ::= */ yytestcase(yyruleno==328);
+ case 330: /* rp_opt ::= */ yytestcase(yyruleno==330);
+ case 348: /* uniqueflag ::= */ yytestcase(yyruleno==348);
+ case 416: /* database_kw_opt ::= */ yytestcase(yyruleno==416);
+ case 433: /* kwcolumn_opt ::= COLUMNKW */ yytestcase(yyruleno==433);
+{yygotominor.yy35 = new bool(false);}
break;
case 23: /* cmd ::= SAVEPOINT nm */
{
- yygotominor.yy41 = new SqliteSavepoint(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteSavepoint(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
case 24: /* cmd ::= RELEASE savepoint_opt nm */
{
- yygotominor.yy41 = new SqliteRelease(*(yymsp[-1].minor.yy225), *(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteRelease(*(yymsp[-1].minor.yy35), *(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
case 25: /* cmd ::= ROLLBACK trans_opt TO savepoint_opt nm */
case 26: /* cmd ::= SAVEPOINT ID_TRANS */ yytestcase(yyruleno==26);
{
- yygotominor.yy41 = new SqliteRollback(
- yymsp[-3].minor.yy512->transactionKw,
- *(yymsp[-1].minor.yy225),
- *(yymsp[0].minor.yy319)
+ yygotominor.yy635 = new SqliteRollback(
+ yymsp[-3].minor.yy100->transactionKw,
+ *(yymsp[-1].minor.yy35),
+ *(yymsp[0].minor.yy255)
);
- delete yymsp[-1].minor.yy225;
- delete yymsp[-3].minor.yy512;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[-3].minor.yy100;
+ objectForTokens = yygotominor.yy635;
}
break;
case 27: /* cmd ::= RELEASE savepoint_opt ID_TRANS */
@@ -3300,114 +3306,114 @@ static void yy_reduce(
break;
case 29: /* cmd ::= CREATE temp TABLE ifnotexists fullname LP columnlist conslist_opt RP table_options */
{
- yygotominor.yy41 = new SqliteCreateTable(
- *(yymsp[-6].minor.yy225),
- *(yymsp[-8].minor.yy130),
- yymsp[-5].minor.yy396->name1,
- yymsp[-5].minor.yy396->name2,
- *(yymsp[-3].minor.yy390),
- *(yymsp[-2].minor.yy115),
- *(yymsp[0].minor.yy455)
+ yygotominor.yy635 = new SqliteCreateTable(
+ *(yymsp[-6].minor.yy35),
+ *(yymsp[-8].minor.yy562),
+ yymsp[-5].minor.yy520->name1,
+ yymsp[-5].minor.yy520->name2,
+ *(yymsp[-3].minor.yy234),
+ *(yymsp[-2].minor.yy445),
+ *(yymsp[0].minor.yy217)
);
- delete yymsp[-6].minor.yy225;
- delete yymsp[-8].minor.yy130;
- delete yymsp[-3].minor.yy390;
- delete yymsp[-2].minor.yy115;
- delete yymsp[-5].minor.yy396;
- delete yymsp[0].minor.yy455;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-6].minor.yy35;
+ delete yymsp[-8].minor.yy562;
+ delete yymsp[-3].minor.yy234;
+ delete yymsp[-2].minor.yy445;
+ delete yymsp[-5].minor.yy520;
+ delete yymsp[0].minor.yy217;
+ objectForTokens = yygotominor.yy635;
}
break;
case 30: /* cmd ::= CREATE temp TABLE ifnotexists fullname AS select */
{
- yygotominor.yy41 = new SqliteCreateTable(
- *(yymsp[-3].minor.yy225),
- *(yymsp[-5].minor.yy130),
- yymsp[-2].minor.yy396->name1,
- yymsp[-2].minor.yy396->name2,
- yymsp[0].minor.yy297
+ yygotominor.yy635 = new SqliteCreateTable(
+ *(yymsp[-3].minor.yy35),
+ *(yymsp[-5].minor.yy562),
+ yymsp[-2].minor.yy520->name1,
+ yymsp[-2].minor.yy520->name2,
+ yymsp[0].minor.yy73
);
- delete yymsp[-3].minor.yy225;
- delete yymsp[-5].minor.yy130;
- delete yymsp[-2].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-3].minor.yy35;
+ delete yymsp[-5].minor.yy562;
+ delete yymsp[-2].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
case 31: /* cmd ::= CREATE temp TABLE ifnotexists nm DOT ID_TAB_NEW */
case 144: /* cmd ::= CREATE temp VIEW ifnotexists nm DOT ID_VIEW_NEW */ yytestcase(yyruleno==144);
- case 383: /* cmd ::= CREATE temp TRIGGER ifnotexists nm DOT ID_TRIG_NEW */ yytestcase(yyruleno==383);
+ case 386: /* cmd ::= CREATE temp TRIGGER ifnotexists nm DOT ID_TRIG_NEW */ yytestcase(yyruleno==386);
{ yy_destructor(yypParser,205,&yymsp[-5].minor);
yy_destructor(yypParser,203,&yymsp[-2].minor);
}
break;
case 32: /* cmd ::= CREATE temp TABLE ifnotexists ID_DB|ID_TAB_NEW */
case 145: /* cmd ::= CREATE temp VIEW ifnotexists ID_DB|ID_VIEW_NEW */ yytestcase(yyruleno==145);
- case 384: /* cmd ::= CREATE temp TRIGGER ifnotexists ID_DB|ID_TRIG_NEW */ yytestcase(yyruleno==384);
+ case 387: /* cmd ::= CREATE temp TRIGGER ifnotexists ID_DB|ID_TRIG_NEW */ yytestcase(yyruleno==387);
{ yy_destructor(yypParser,205,&yymsp[-3].minor);
}
break;
case 33: /* table_options ::= */
-{yygotominor.yy455 = new ParserCreateTableOptionList();}
+{yygotominor.yy217 = new ParserCreateTableOptionList();}
break;
case 34: /* table_options ::= table_option */
{
- yygotominor.yy455 = new ParserCreateTableOptionList();
- yygotominor.yy455->append(yymsp[0].minor.yy629);
+ yygotominor.yy217 = new ParserCreateTableOptionList();
+ yygotominor.yy217->append(yymsp[0].minor.yy607);
}
break;
case 35: /* table_options ::= table_options COMMA table_option */
{
- yymsp[-2].minor.yy455->append(yymsp[0].minor.yy629);
- yygotominor.yy455 = yymsp[-2].minor.yy455;
+ yymsp[-2].minor.yy217->append(yymsp[0].minor.yy607);
+ yygotominor.yy217 = yymsp[-2].minor.yy217;
DONT_INHERIT_TOKENS("table_options");
}
break;
case 36: /* table_option ::= WITHOUT nm */
{
- if (yymsp[0].minor.yy319->toLower() != "rowid")
- parserContext->errorAtToken(QString("Invalid table option: %1").arg(*(yymsp[0].minor.yy319)));
+ if (yymsp[0].minor.yy255->toLower() != "rowid")
+ parserContext->errorAtToken(QString("Invalid table option: %1").arg(*(yymsp[0].minor.yy255)));
- yygotominor.yy629 = new ParserStubCreateTableOption(ParserStubCreateTableOption::WITHOUT_ROWID);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy607 = new ParserStubCreateTableOption(ParserStubCreateTableOption::WITHOUT_ROWID);
+ delete yymsp[0].minor.yy255;
}
break;
case 37: /* table_option ::= nm */
case 38: /* table_option ::= WITHOUT CTX_ROWID_KW */ yytestcase(yyruleno==38);
case 39: /* table_option ::= CTX_STRICT_KW */ yytestcase(yyruleno==39);
{
- if (yymsp[0].minor.yy319->toLower() != "strict")
- parserContext->errorAtToken(QString("Invalid table option: %1").arg(*(yymsp[0].minor.yy319)));
+ if (yymsp[0].minor.yy255->toLower() != "strict")
+ parserContext->errorAtToken(QString("Invalid table option: %1").arg(*(yymsp[0].minor.yy255)));
- yygotominor.yy629 = new ParserStubCreateTableOption(ParserStubCreateTableOption::STRICT);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy607 = new ParserStubCreateTableOption(ParserStubCreateTableOption::STRICT);
+ delete yymsp[0].minor.yy255;
}
break;
case 42: /* temp ::= TEMP */
-{yygotominor.yy130 = new int( (yymsp[0].minor.yy0->value.length() > 4) ? 2 : 1 );}
+{yygotominor.yy562 = new int( (yymsp[0].minor.yy0->value.length() > 4) ? 2 : 1 );}
break;
case 43: /* temp ::= */
case 166: /* distinct ::= */ yytestcase(yyruleno==166);
-{yygotominor.yy130 = new int(0);}
+{yygotominor.yy562 = new int(0);}
break;
case 44: /* columnlist ::= columnlist COMMA column */
{
- yymsp[-2].minor.yy390->append(yymsp[0].minor.yy3);
- yygotominor.yy390 = yymsp[-2].minor.yy390;
+ yymsp[-2].minor.yy234->append(yymsp[0].minor.yy115);
+ yygotominor.yy234 = yymsp[-2].minor.yy234;
DONT_INHERIT_TOKENS("columnlist");
}
break;
case 45: /* columnlist ::= column */
{
- yygotominor.yy390 = new ParserCreateTableColumnList();
- yygotominor.yy390->append(yymsp[0].minor.yy3);
+ yygotominor.yy234 = new ParserCreateTableColumnList();
+ yygotominor.yy234->append(yymsp[0].minor.yy115);
}
break;
case 46: /* column ::= columnid type carglist */
{
- yygotominor.yy3 = new SqliteCreateTable::Column(*(yymsp[-2].minor.yy319), yymsp[-1].minor.yy267, *(yymsp[0].minor.yy323));
- delete yymsp[-2].minor.yy319;
- delete yymsp[0].minor.yy323;
- objectForTokens = yygotominor.yy3;
+ yygotominor.yy115 = new SqliteCreateTable::Column(*(yymsp[-2].minor.yy255), yymsp[-1].minor.yy601, *(yymsp[0].minor.yy259));
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[0].minor.yy259;
+ objectForTokens = yygotominor.yy115;
}
break;
case 47: /* columnid ::= nm */
@@ -3415,13 +3421,13 @@ static void yy_reduce(
case 53: /* nm ::= id */ yytestcase(yyruleno==53);
case 61: /* typename ::= ids */ yytestcase(yyruleno==61);
case 199: /* dbnm ::= DOT nm */ yytestcase(yyruleno==199);
- case 353: /* collate ::= COLLATE ids */ yytestcase(yyruleno==353);
- case 354: /* collate ::= COLLATE ID_COLLATE */ yytestcase(yyruleno==354);
-{yygotominor.yy319 = yymsp[0].minor.yy319;}
+ case 356: /* collate ::= COLLATE ids */ yytestcase(yyruleno==356);
+ case 357: /* collate ::= COLLATE ID_COLLATE */ yytestcase(yyruleno==357);
+{yygotominor.yy255 = yymsp[0].minor.yy255;}
break;
case 49: /* id ::= ID */
{
- yygotominor.yy319 = new QString(
+ yygotominor.yy255 = new QString(
stripObjName(
yymsp[0].minor.yy0->value
)
@@ -3430,195 +3436,195 @@ static void yy_reduce(
break;
case 50: /* id_opt ::= id */
{
- yygotominor.yy319 = yymsp[0].minor.yy319;
+ yygotominor.yy255 = yymsp[0].minor.yy255;
}
break;
case 51: /* id_opt ::= */
{
- yygotominor.yy319 = new QString();
+ yygotominor.yy255 = new QString();
}
break;
case 52: /* ids ::= ID|STRING */
case 55: /* nm ::= JOIN_KW */ yytestcase(yyruleno==55);
-{yygotominor.yy319 = new QString(yymsp[0].minor.yy0->value);}
+{yygotominor.yy255 = new QString(yymsp[0].minor.yy0->value);}
break;
case 54: /* nm ::= STRING */
-{yygotominor.yy319 = new QString(stripString(yymsp[0].minor.yy0->value));}
+{yygotominor.yy255 = new QString(stripString(yymsp[0].minor.yy0->value));}
break;
case 56: /* type ::= */
-{yygotominor.yy267 = nullptr;}
+{yygotominor.yy601 = nullptr;}
break;
case 57: /* type ::= typetoken */
-{yygotominor.yy267 = yymsp[0].minor.yy267;}
+{yygotominor.yy601 = yymsp[0].minor.yy601;}
break;
case 58: /* typetoken ::= typename */
{
- yygotominor.yy267 = new SqliteColumnType(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy267;
+ yygotominor.yy601 = new SqliteColumnType(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy601;
}
break;
case 59: /* typetoken ::= typename LP signed RP */
{
- yygotominor.yy267 = new SqliteColumnType(*(yymsp[-3].minor.yy319), *(yymsp[-1].minor.yy393));
- delete yymsp[-3].minor.yy319;
- delete yymsp[-1].minor.yy393;
- objectForTokens = yygotominor.yy267;
+ yygotominor.yy601 = new SqliteColumnType(*(yymsp[-3].minor.yy255), *(yymsp[-1].minor.yy629));
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-1].minor.yy629;
+ objectForTokens = yygotominor.yy601;
}
break;
case 60: /* typetoken ::= typename LP signed COMMA signed RP */
{
- yygotominor.yy267 = new SqliteColumnType(*(yymsp[-5].minor.yy319), *(yymsp[-3].minor.yy393), *(yymsp[-1].minor.yy393));
- delete yymsp[-5].minor.yy319;
- delete yymsp[-3].minor.yy393;
- delete yymsp[-1].minor.yy393;
- objectForTokens = yygotominor.yy267;
+ yygotominor.yy601 = new SqliteColumnType(*(yymsp[-5].minor.yy255), *(yymsp[-3].minor.yy629), *(yymsp[-1].minor.yy629));
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-3].minor.yy629;
+ delete yymsp[-1].minor.yy629;
+ objectForTokens = yygotominor.yy601;
}
break;
case 62: /* typename ::= typename ids */
case 63: /* typename ::= ID_COL_TYPE */ yytestcase(yyruleno==63);
{
- yymsp[-1].minor.yy319->append(" " + *(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- yygotominor.yy319 = yymsp[-1].minor.yy319;
+ yymsp[-1].minor.yy255->append(" " + *(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ yygotominor.yy255 = yymsp[-1].minor.yy255;
}
break;
case 64: /* signed ::= plus_num */
case 65: /* signed ::= minus_num */ yytestcase(yyruleno==65);
- case 369: /* nmnum ::= plus_num */ yytestcase(yyruleno==369);
- case 374: /* plus_num ::= PLUS number */ yytestcase(yyruleno==374);
- case 375: /* plus_num ::= number */ yytestcase(yyruleno==375);
-{yygotominor.yy393 = yymsp[0].minor.yy393;}
+ case 372: /* nmnum ::= plus_num */ yytestcase(yyruleno==372);
+ case 377: /* plus_num ::= PLUS number */ yytestcase(yyruleno==377);
+ case 378: /* plus_num ::= number */ yytestcase(yyruleno==378);
+{yygotominor.yy629 = yymsp[0].minor.yy629;}
break;
case 66: /* carglist ::= carglist ccons */
{
- yymsp[-1].minor.yy323->append(yymsp[0].minor.yy448);
- yygotominor.yy323 = yymsp[-1].minor.yy323;
+ yymsp[-1].minor.yy259->append(yymsp[0].minor.yy64);
+ yygotominor.yy259 = yymsp[-1].minor.yy259;
DONT_INHERIT_TOKENS("carglist");
}
break;
case 67: /* carglist ::= */
-{yygotominor.yy323 = new ParserCreateTableColumnConstraintList();}
+{yygotominor.yy259 = new ParserCreateTableColumnConstraintList();}
break;
case 68: /* ccons ::= CONSTRAINT nm */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefNameOnly(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefNameOnly(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy64;
}
break;
case 69: /* ccons ::= DEFAULT term */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefTerm(*(yymsp[0].minor.yy393));
- delete yymsp[0].minor.yy393;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefTerm(*(yymsp[0].minor.yy629));
+ delete yymsp[0].minor.yy629;
+ objectForTokens = yygotominor.yy64;
}
break;
case 70: /* ccons ::= DEFAULT LP expr RP */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefExpr(yymsp[-1].minor.yy186);
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefExpr(yymsp[-1].minor.yy176);
+ objectForTokens = yygotominor.yy64;
}
break;
case 71: /* ccons ::= DEFAULT PLUS term */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefTerm(*(yymsp[0].minor.yy393), false);
- delete yymsp[0].minor.yy393;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefTerm(*(yymsp[0].minor.yy629), false);
+ delete yymsp[0].minor.yy629;
+ objectForTokens = yygotominor.yy64;
}
break;
case 72: /* ccons ::= DEFAULT MINUS term */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefTerm(*(yymsp[0].minor.yy393), true);
- delete yymsp[0].minor.yy393;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefTerm(*(yymsp[0].minor.yy629), true);
+ delete yymsp[0].minor.yy629;
+ objectForTokens = yygotominor.yy64;
}
break;
case 73: /* ccons ::= DEFAULT id */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefId(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefId(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy64;
}
break;
case 74: /* ccons ::= DEFAULT CTIME_KW */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefCTime(yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefCTime(yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy64;
}
break;
case 75: /* ccons ::= NULL onconf */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initNull(*(yymsp[0].minor.yy136));
- delete yymsp[0].minor.yy136;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initNull(*(yymsp[0].minor.yy66));
+ delete yymsp[0].minor.yy66;
+ objectForTokens = yygotominor.yy64;
}
break;
case 76: /* ccons ::= NOT NULL onconf */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initNotNull(*(yymsp[0].minor.yy136));
- delete yymsp[0].minor.yy136;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initNotNull(*(yymsp[0].minor.yy66));
+ delete yymsp[0].minor.yy66;
+ objectForTokens = yygotominor.yy64;
}
break;
case 77: /* ccons ::= PRIMARY KEY sortorder onconf autoinc */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initPk(*(yymsp[-2].minor.yy35), *(yymsp[-1].minor.yy136), *(yymsp[0].minor.yy225));
- delete yymsp[-2].minor.yy35;
- delete yymsp[0].minor.yy225;
- delete yymsp[-1].minor.yy136;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initPk(*(yymsp[-2].minor.yy645), *(yymsp[-1].minor.yy66), *(yymsp[0].minor.yy35));
+ delete yymsp[-2].minor.yy645;
+ delete yymsp[0].minor.yy35;
+ delete yymsp[-1].minor.yy66;
+ objectForTokens = yygotominor.yy64;
}
break;
case 78: /* ccons ::= UNIQUE onconf */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initUnique(*(yymsp[0].minor.yy136));
- delete yymsp[0].minor.yy136;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initUnique(*(yymsp[0].minor.yy66));
+ delete yymsp[0].minor.yy66;
+ objectForTokens = yygotominor.yy64;
}
break;
case 79: /* ccons ::= CHECK LP expr RP */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initCheck(yymsp[-1].minor.yy186);
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initCheck(yymsp[-1].minor.yy176);
+ objectForTokens = yygotominor.yy64;
}
break;
case 80: /* ccons ::= REFERENCES nm idxlist_opt refargs */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initFk(*(yymsp[-2].minor.yy319), *(yymsp[-1].minor.yy627), *(yymsp[0].minor.yy156));
- delete yymsp[-2].minor.yy319;
- delete yymsp[0].minor.yy156;
- delete yymsp[-1].minor.yy627;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initFk(*(yymsp[-2].minor.yy255), *(yymsp[-1].minor.yy527), *(yymsp[0].minor.yy56));
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[0].minor.yy56;
+ delete yymsp[-1].minor.yy527;
+ objectForTokens = yygotominor.yy64;
}
break;
case 81: /* ccons ::= defer_subclause */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initDefer(yymsp[0].minor.yy53->initially, yymsp[0].minor.yy53->deferrable);
- delete yymsp[0].minor.yy53;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initDefer(yymsp[0].minor.yy218->initially, yymsp[0].minor.yy218->deferrable);
+ delete yymsp[0].minor.yy218;
+ objectForTokens = yygotominor.yy64;
}
break;
case 82: /* ccons ::= COLLATE ids */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initColl(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initColl(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy64;
}
break;
case 83: /* ccons ::= gen_always AS LP expr RP id_opt */
@@ -3626,227 +3632,227 @@ static void yy_reduce(
case 85: /* ccons ::= COLLATE ID_COLLATE */ yytestcase(yyruleno==85);
case 86: /* ccons ::= REFERENCES ID_TAB */ yytestcase(yyruleno==86);
{
- if (!yymsp[0].minor.yy319->isNull() && yymsp[0].minor.yy319->toLower() != "stored" && yymsp[0].minor.yy319->toLower() != "virtual")
- parserContext->errorAtToken(QString("Invalid generated column type: %1").arg(*(yymsp[0].minor.yy319)));
+ if (!yymsp[0].minor.yy255->isNull() && yymsp[0].minor.yy255->toLower() != "stored" && yymsp[0].minor.yy255->toLower() != "virtual")
+ parserContext->errorAtToken(QString("Invalid generated column type: %1").arg(*(yymsp[0].minor.yy255)));
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initGeneratedAs(yymsp[-2].minor.yy186, *(yymsp[-5].minor.yy225), *(yymsp[0].minor.yy319));
- delete yymsp[-5].minor.yy225;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initGeneratedAs(yymsp[-2].minor.yy176, *(yymsp[-5].minor.yy35), *(yymsp[0].minor.yy255));
+ delete yymsp[-5].minor.yy35;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy64;
}
break;
case 87: /* ccons ::= CHECK LP RP */
{
- yygotominor.yy448 = new SqliteCreateTable::Column::Constraint();
- yygotominor.yy448->initCheck();
- objectForTokens = yygotominor.yy448;
+ yygotominor.yy64 = new SqliteCreateTable::Column::Constraint();
+ yygotominor.yy64->initCheck();
+ objectForTokens = yygotominor.yy64;
parserContext->minorErrorAfterLastToken("Syntax error");
}
break;
case 88: /* term ::= NULL */
-{yygotominor.yy393 = new QVariant();}
+{yygotominor.yy629 = new QVariant();}
break;
case 89: /* term ::= INTEGER */
- case 377: /* number ::= INTEGER */ yytestcase(yyruleno==377);
-{yygotominor.yy393 = parserContext->handleNumberToken(yymsp[0].minor.yy0->value);}
+ case 380: /* number ::= INTEGER */ yytestcase(yyruleno==380);
+{yygotominor.yy629 = parserContext->handleNumberToken(yymsp[0].minor.yy0->value);}
break;
case 90: /* term ::= FLOAT */
- case 378: /* number ::= FLOAT */ yytestcase(yyruleno==378);
-{yygotominor.yy393 = new QVariant(QVariant(yymsp[0].minor.yy0->value).toDouble());}
+ case 381: /* number ::= FLOAT */ yytestcase(yyruleno==381);
+{yygotominor.yy629 = new QVariant(QVariant(yymsp[0].minor.yy0->value).toDouble());}
break;
case 91: /* term ::= STRING|BLOB */
{
if (yymsp[0].minor.yy0->value.length() >= 3 && yymsp[0].minor.yy0->value.startsWith("x'", Qt::CaseInsensitive))
- yygotominor.yy393 = new QVariant(blobFromLiteral(yymsp[0].minor.yy0->value));
+ yygotominor.yy629 = new QVariant(blobFromLiteral(yymsp[0].minor.yy0->value));
else
- yygotominor.yy393 = new QVariant(stripString(yymsp[0].minor.yy0->value));
+ yygotominor.yy629 = new QVariant(stripString(yymsp[0].minor.yy0->value));
}
break;
case 92: /* tnm ::= term */
{
- yygotominor.yy380 = new ParserTermOrLiteral(*(yymsp[0].minor.yy393));
- delete yymsp[0].minor.yy393;
+ yygotominor.yy542 = new ParserTermOrLiteral(*(yymsp[0].minor.yy629));
+ delete yymsp[0].minor.yy629;
}
break;
case 93: /* tnm ::= nm */
{
- yygotominor.yy380 = new ParserTermOrLiteral(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
+ yygotominor.yy542 = new ParserTermOrLiteral(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
}
break;
case 98: /* refargs ::= */
-{yygotominor.yy156 = new ParserFkConditionList();}
+{yygotominor.yy56 = new ParserFkConditionList();}
break;
case 99: /* refargs ::= refargs refarg */
{
- yymsp[-1].minor.yy156->append(yymsp[0].minor.yy205);
- yygotominor.yy156 = yymsp[-1].minor.yy156;
+ yymsp[-1].minor.yy56->append(yymsp[0].minor.yy587);
+ yygotominor.yy56 = yymsp[-1].minor.yy56;
DONT_INHERIT_TOKENS("refargs");
}
break;
case 100: /* refarg ::= MATCH nm */
{
- yygotominor.yy205 = new SqliteForeignKey::Condition(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
+ yygotominor.yy587 = new SqliteForeignKey::Condition(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
}
break;
case 101: /* refarg ::= ON INSERT refact */
-{yygotominor.yy205 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::INSERT, *(yymsp[0].minor.yy106)); delete yymsp[0].minor.yy106;}
+{yygotominor.yy587 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::INSERT, *(yymsp[0].minor.yy488)); delete yymsp[0].minor.yy488;}
break;
case 102: /* refarg ::= ON DELETE refact */
-{yygotominor.yy205 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::DELETE, *(yymsp[0].minor.yy106)); delete yymsp[0].minor.yy106;}
+{yygotominor.yy587 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::DELETE, *(yymsp[0].minor.yy488)); delete yymsp[0].minor.yy488;}
break;
case 103: /* refarg ::= ON UPDATE refact */
case 104: /* refarg ::= MATCH ID_FK_MATCH */ yytestcase(yyruleno==104);
-{yygotominor.yy205 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::UPDATE, *(yymsp[0].minor.yy106)); delete yymsp[0].minor.yy106;}
+{yygotominor.yy587 = new SqliteForeignKey::Condition(SqliteForeignKey::Condition::UPDATE, *(yymsp[0].minor.yy488)); delete yymsp[0].minor.yy488;}
break;
case 105: /* refact ::= SET NULL */
-{yygotominor.yy106 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::SET_NULL);}
+{yygotominor.yy488 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::SET_NULL);}
break;
case 106: /* refact ::= SET DEFAULT */
-{yygotominor.yy106 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::SET_DEFAULT);}
+{yygotominor.yy488 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::SET_DEFAULT);}
break;
case 107: /* refact ::= CASCADE */
-{yygotominor.yy106 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::CASCADE);}
+{yygotominor.yy488 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::CASCADE);}
break;
case 108: /* refact ::= RESTRICT */
-{yygotominor.yy106 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::RESTRICT);}
+{yygotominor.yy488 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::RESTRICT);}
break;
case 109: /* refact ::= NO ACTION */
-{yygotominor.yy106 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::NO_ACTION);}
+{yygotominor.yy488 = new SqliteForeignKey::Condition::Reaction(SqliteForeignKey::Condition::NO_ACTION);}
break;
case 110: /* defer_subclause ::= NOT DEFERRABLE init_deferred_pred_opt */
{
- yygotominor.yy53 = new ParserDeferSubClause(SqliteDeferrable::NOT_DEFERRABLE, *(yymsp[0].minor.yy612));
- delete yymsp[0].minor.yy612;
+ yygotominor.yy218 = new ParserDeferSubClause(SqliteDeferrable::NOT_DEFERRABLE, *(yymsp[0].minor.yy536));
+ delete yymsp[0].minor.yy536;
}
break;
case 111: /* defer_subclause ::= DEFERRABLE init_deferred_pred_opt */
{
- yygotominor.yy53 = new ParserDeferSubClause(SqliteDeferrable::DEFERRABLE, *(yymsp[0].minor.yy612));
- delete yymsp[0].minor.yy612;
+ yygotominor.yy218 = new ParserDeferSubClause(SqliteDeferrable::DEFERRABLE, *(yymsp[0].minor.yy536));
+ delete yymsp[0].minor.yy536;
}
break;
case 112: /* init_deferred_pred_opt ::= */
-{yygotominor.yy612 = new SqliteInitially(SqliteInitially::null);}
+{yygotominor.yy536 = new SqliteInitially(SqliteInitially::null);}
break;
case 113: /* init_deferred_pred_opt ::= INITIALLY DEFERRED */
-{yygotominor.yy612 = new SqliteInitially(SqliteInitially::DEFERRED);}
+{yygotominor.yy536 = new SqliteInitially(SqliteInitially::DEFERRED);}
break;
case 114: /* init_deferred_pred_opt ::= INITIALLY IMMEDIATE */
-{yygotominor.yy612 = new SqliteInitially(SqliteInitially::IMMEDIATE);}
+{yygotominor.yy536 = new SqliteInitially(SqliteInitially::IMMEDIATE);}
break;
case 115: /* conslist_opt ::= */
-{yygotominor.yy115 = new ParserCreateTableConstraintList();}
+{yygotominor.yy445 = new ParserCreateTableConstraintList();}
break;
case 116: /* conslist_opt ::= COMMA conslist */
-{yygotominor.yy115 = yymsp[0].minor.yy115;}
+{yygotominor.yy445 = yymsp[0].minor.yy445;}
break;
case 117: /* conslist ::= conslist tconscomma tcons */
{
- yymsp[0].minor.yy400->afterComma = *(yymsp[-1].minor.yy225);
- yymsp[-2].minor.yy115->append(yymsp[0].minor.yy400);
- yygotominor.yy115 = yymsp[-2].minor.yy115;
- delete yymsp[-1].minor.yy225;
+ yymsp[0].minor.yy166->afterComma = *(yymsp[-1].minor.yy35);
+ yymsp[-2].minor.yy445->append(yymsp[0].minor.yy166);
+ yygotominor.yy445 = yymsp[-2].minor.yy445;
+ delete yymsp[-1].minor.yy35;
DONT_INHERIT_TOKENS("conslist");
}
break;
case 118: /* conslist ::= tcons */
{
- yygotominor.yy115 = new ParserCreateTableConstraintList();
- yygotominor.yy115->append(yymsp[0].minor.yy400);
+ yygotominor.yy445 = new ParserCreateTableConstraintList();
+ yygotominor.yy445->append(yymsp[0].minor.yy166);
}
break;
case 121: /* tcons ::= CONSTRAINT nm */
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initNameOnly(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy400;
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initNameOnly(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy166;
}
break;
case 122: /* tcons ::= PRIMARY KEY LP idxlist autoinc RP onconf */
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initPk(*(yymsp[-3].minor.yy627), *(yymsp[-2].minor.yy225), *(yymsp[0].minor.yy136));
- delete yymsp[-2].minor.yy225;
- delete yymsp[0].minor.yy136;
- delete yymsp[-3].minor.yy627;
- objectForTokens = yygotominor.yy400;
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initPk(*(yymsp[-3].minor.yy527), *(yymsp[-2].minor.yy35), *(yymsp[0].minor.yy66));
+ delete yymsp[-2].minor.yy35;
+ delete yymsp[0].minor.yy66;
+ delete yymsp[-3].minor.yy527;
+ objectForTokens = yygotominor.yy166;
}
break;
case 123: /* tcons ::= UNIQUE LP idxlist RP onconf */
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initUnique(*(yymsp[-2].minor.yy627), *(yymsp[0].minor.yy136));
- delete yymsp[0].minor.yy136;
- delete yymsp[-2].minor.yy627;
- objectForTokens = yygotominor.yy400;
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initUnique(*(yymsp[-2].minor.yy527), *(yymsp[0].minor.yy66));
+ delete yymsp[0].minor.yy66;
+ delete yymsp[-2].minor.yy527;
+ objectForTokens = yygotominor.yy166;
}
break;
case 124: /* tcons ::= CHECK LP expr RP onconf */
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initCheck(yymsp[-2].minor.yy186, *(yymsp[0].minor.yy136));
- objectForTokens = yygotominor.yy400;
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initCheck(yymsp[-2].minor.yy176, *(yymsp[0].minor.yy66));
+ objectForTokens = yygotominor.yy166;
}
break;
case 125: /* tcons ::= FOREIGN KEY LP idxlist RP REFERENCES nm idxlist_opt refargs defer_subclause_opt */
case 126: /* tcons ::= CONSTRAINT ID_CONSTR */ yytestcase(yyruleno==126);
case 127: /* tcons ::= FOREIGN KEY LP idxlist RP REFERENCES ID_TAB */ yytestcase(yyruleno==127);
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initFk(
- *(yymsp[-6].minor.yy627),
- *(yymsp[-3].minor.yy319),
- *(yymsp[-2].minor.yy627),
- *(yymsp[-1].minor.yy156),
- yymsp[0].minor.yy53->initially,
- yymsp[0].minor.yy53->deferrable
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initFk(
+ *(yymsp[-6].minor.yy527),
+ *(yymsp[-3].minor.yy255),
+ *(yymsp[-2].minor.yy527),
+ *(yymsp[-1].minor.yy56),
+ yymsp[0].minor.yy218->initially,
+ yymsp[0].minor.yy218->deferrable
);
- delete yymsp[-3].minor.yy319;
- delete yymsp[-1].minor.yy156;
- delete yymsp[0].minor.yy53;
- delete yymsp[-2].minor.yy627;
- delete yymsp[-6].minor.yy627;
- objectForTokens = yygotominor.yy400;
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-1].minor.yy56;
+ delete yymsp[0].minor.yy218;
+ delete yymsp[-2].minor.yy527;
+ delete yymsp[-6].minor.yy527;
+ objectForTokens = yygotominor.yy166;
}
break;
case 128: /* tcons ::= CHECK LP RP onconf */
{
- yygotominor.yy400 = new SqliteCreateTable::Constraint();
- yygotominor.yy400->initCheck();
- objectForTokens = yygotominor.yy400;
+ yygotominor.yy166 = new SqliteCreateTable::Constraint();
+ yygotominor.yy166->initCheck();
+ objectForTokens = yygotominor.yy166;
parserContext->minorErrorAfterLastToken("Syntax error");
yy_destructor(yypParser,228,&yymsp[0].minor);
}
break;
case 129: /* defer_subclause_opt ::= */
-{yygotominor.yy53 = new ParserDeferSubClause(SqliteDeferrable::null, SqliteInitially::null);}
+{yygotominor.yy218 = new ParserDeferSubClause(SqliteDeferrable::null, SqliteInitially::null);}
break;
case 130: /* defer_subclause_opt ::= defer_subclause */
-{yygotominor.yy53 = yymsp[0].minor.yy53;}
+{yygotominor.yy218 = yymsp[0].minor.yy218;}
break;
case 131: /* onconf ::= */
case 133: /* orconf ::= */ yytestcase(yyruleno==133);
-{yygotominor.yy136 = new SqliteConflictAlgo(SqliteConflictAlgo::null);}
+{yygotominor.yy66 = new SqliteConflictAlgo(SqliteConflictAlgo::null);}
break;
case 132: /* onconf ::= ON CONFLICT resolvetype */
case 134: /* orconf ::= OR resolvetype */ yytestcase(yyruleno==134);
-{yygotominor.yy136 = yymsp[0].minor.yy136;}
+{yygotominor.yy66 = yymsp[0].minor.yy66;}
break;
case 135: /* resolvetype ::= raisetype */
case 136: /* resolvetype ::= IGNORE */ yytestcase(yyruleno==136);
case 137: /* resolvetype ::= REPLACE */ yytestcase(yyruleno==137);
-{yygotominor.yy136 = new SqliteConflictAlgo(sqliteConflictAlgo(yymsp[0].minor.yy0->value));}
+{yygotominor.yy66 = new SqliteConflictAlgo(sqliteConflictAlgo(yymsp[0].minor.yy0->value));}
break;
case 138: /* cmd ::= DROP TABLE ifexists fullname */
{
- yygotominor.yy41 = new SqliteDropTable(*(yymsp[-1].minor.yy225), yymsp[0].minor.yy396->name1, yymsp[0].minor.yy396->name2);
- delete yymsp[-1].minor.yy225;
- delete yymsp[0].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteDropTable(*(yymsp[-1].minor.yy35), yymsp[0].minor.yy520->name1, yymsp[0].minor.yy520->name2);
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[0].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
case 139: /* cmd ::= DROP TABLE ifexists nm DOT ID_TAB */
@@ -3857,41 +3863,41 @@ static void yy_reduce(
case 192: /* singlesrc ::= ID_DB|ID_TAB */ yytestcase(yyruleno==192);
case 193: /* singlesrc ::= nm DOT ID_VIEW */ yytestcase(yyruleno==193);
case 194: /* singlesrc ::= ID_DB|ID_VIEW */ yytestcase(yyruleno==194);
- case 342: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm DOT ID_IDX_NEW */ yytestcase(yyruleno==342);
- case 343: /* cmd ::= CREATE uniqueflag INDEX ifnotexists ID_DB|ID_IDX_NEW */ yytestcase(yyruleno==343);
- case 356: /* cmd ::= DROP INDEX ifexists nm DOT ID_IDX */ yytestcase(yyruleno==356);
- case 357: /* cmd ::= DROP INDEX ifexists ID_DB|ID_IDX */ yytestcase(yyruleno==357);
- case 367: /* cmd ::= PRAGMA nm DOT ID_PRAGMA */ yytestcase(yyruleno==367);
- case 368: /* cmd ::= PRAGMA ID_DB|ID_PRAGMA */ yytestcase(yyruleno==368);
- case 406: /* cmd ::= DROP TRIGGER ifexists nm DOT ID_TRIG */ yytestcase(yyruleno==406);
- case 407: /* cmd ::= DROP TRIGGER ifexists ID_DB|ID_TRIG */ yytestcase(yyruleno==407);
- case 417: /* cmd ::= REINDEX nm DOT ID_TAB|ID_IDX */ yytestcase(yyruleno==417);
- case 418: /* cmd ::= REINDEX ID_DB|ID_IDX|ID_TAB */ yytestcase(yyruleno==418);
- case 421: /* cmd ::= ANALYZE nm DOT ID_TAB|ID_IDX */ yytestcase(yyruleno==421);
- case 422: /* cmd ::= ANALYZE ID_DB|ID_IDX|ID_TAB */ yytestcase(yyruleno==422);
- case 427: /* cmd ::= ALTER TABLE nm DOT ID_TAB */ yytestcase(yyruleno==427);
- case 428: /* cmd ::= ALTER TABLE ID_DB|ID_TAB */ yytestcase(yyruleno==428);
- case 434: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm DOT ID_TAB_NEW */ yytestcase(yyruleno==434);
- case 435: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists ID_DB|ID_TAB_NEW */ yytestcase(yyruleno==435);
+ case 345: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm DOT ID_IDX_NEW */ yytestcase(yyruleno==345);
+ case 346: /* cmd ::= CREATE uniqueflag INDEX ifnotexists ID_DB|ID_IDX_NEW */ yytestcase(yyruleno==346);
+ case 359: /* cmd ::= DROP INDEX ifexists nm DOT ID_IDX */ yytestcase(yyruleno==359);
+ case 360: /* cmd ::= DROP INDEX ifexists ID_DB|ID_IDX */ yytestcase(yyruleno==360);
+ case 370: /* cmd ::= PRAGMA nm DOT ID_PRAGMA */ yytestcase(yyruleno==370);
+ case 371: /* cmd ::= PRAGMA ID_DB|ID_PRAGMA */ yytestcase(yyruleno==371);
+ case 409: /* cmd ::= DROP TRIGGER ifexists nm DOT ID_TRIG */ yytestcase(yyruleno==409);
+ case 410: /* cmd ::= DROP TRIGGER ifexists ID_DB|ID_TRIG */ yytestcase(yyruleno==410);
+ case 420: /* cmd ::= REINDEX nm DOT ID_TAB|ID_IDX */ yytestcase(yyruleno==420);
+ case 421: /* cmd ::= REINDEX ID_DB|ID_IDX|ID_TAB */ yytestcase(yyruleno==421);
+ case 424: /* cmd ::= ANALYZE nm DOT ID_TAB|ID_IDX */ yytestcase(yyruleno==424);
+ case 425: /* cmd ::= ANALYZE ID_DB|ID_IDX|ID_TAB */ yytestcase(yyruleno==425);
+ case 430: /* cmd ::= ALTER TABLE nm DOT ID_TAB */ yytestcase(yyruleno==430);
+ case 431: /* cmd ::= ALTER TABLE ID_DB|ID_TAB */ yytestcase(yyruleno==431);
+ case 437: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm DOT ID_TAB_NEW */ yytestcase(yyruleno==437);
+ case 438: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists ID_DB|ID_TAB_NEW */ yytestcase(yyruleno==438);
{ yy_destructor(yypParser,203,&yymsp[-2].minor);
}
break;
case 143: /* cmd ::= CREATE temp VIEW ifnotexists fullname idxlist_opt AS select */
{
- yygotominor.yy41 = new SqliteCreateView(*(yymsp[-6].minor.yy130), *(yymsp[-4].minor.yy225), yymsp[-3].minor.yy396->name1, yymsp[-3].minor.yy396->name2, yymsp[0].minor.yy297, *(yymsp[-2].minor.yy627));
- delete yymsp[-6].minor.yy130;
- delete yymsp[-4].minor.yy225;
- delete yymsp[-3].minor.yy396;
- delete yymsp[-2].minor.yy627;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteCreateView(*(yymsp[-6].minor.yy562), *(yymsp[-4].minor.yy35), yymsp[-3].minor.yy520->name1, yymsp[-3].minor.yy520->name2, yymsp[0].minor.yy73, *(yymsp[-2].minor.yy527));
+ delete yymsp[-6].minor.yy562;
+ delete yymsp[-4].minor.yy35;
+ delete yymsp[-3].minor.yy520;
+ delete yymsp[-2].minor.yy527;
+ objectForTokens = yygotominor.yy635;
}
break;
case 146: /* cmd ::= DROP VIEW ifexists fullname */
{
- yygotominor.yy41 = new SqliteDropView(*(yymsp[-1].minor.yy225), yymsp[0].minor.yy396->name1, yymsp[0].minor.yy396->name2);
- delete yymsp[-1].minor.yy225;
- delete yymsp[0].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteDropView(*(yymsp[-1].minor.yy35), yymsp[0].minor.yy520->name1, yymsp[0].minor.yy520->name2);
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[0].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
case 149: /* cmd ::= select_stmt */
@@ -3899,143 +3905,143 @@ static void yy_reduce(
case 241: /* cmd ::= update_stmt */ yytestcase(yyruleno==241);
case 262: /* cmd ::= insert_stmt */ yytestcase(yyruleno==262);
{
- yygotominor.yy41 = yymsp[0].minor.yy41;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = yymsp[0].minor.yy635;
+ objectForTokens = yygotominor.yy635;
}
break;
case 150: /* select_stmt ::= select */
{
- yygotominor.yy41 = yymsp[0].minor.yy297;
+ yygotominor.yy635 = yymsp[0].minor.yy73;
// since it's used in trigger:
- objectForTokens = yygotominor.yy41;
+ objectForTokens = yygotominor.yy635;
}
break;
case 151: /* select ::= with selectnowith */
{
- yygotominor.yy297 = yymsp[0].minor.yy297;
- yymsp[0].minor.yy297->setWith(yymsp[-1].minor.yy161);
- objectForTokens = yygotominor.yy297;
+ yygotominor.yy73 = yymsp[0].minor.yy73;
+ yymsp[0].minor.yy73->setWith(yymsp[-1].minor.yy321);
+ objectForTokens = yygotominor.yy73;
}
break;
case 152: /* selectnowith ::= oneselect */
{
- yygotominor.yy297 = SqliteSelect::append(yymsp[0].minor.yy378);
- objectForTokens = yygotominor.yy297;
+ yygotominor.yy73 = SqliteSelect::append(yymsp[0].minor.yy438);
+ objectForTokens = yygotominor.yy73;
}
break;
case 153: /* selectnowith ::= selectnowith multiselect_op oneselect */
{
- yygotominor.yy297 = SqliteSelect::append(yymsp[-2].minor.yy297, *(yymsp[-1].minor.yy142), yymsp[0].minor.yy378);
- delete yymsp[-1].minor.yy142;
- objectForTokens = yygotominor.yy297;
+ yygotominor.yy73 = SqliteSelect::append(yymsp[-2].minor.yy73, *(yymsp[-1].minor.yy574), yymsp[0].minor.yy438);
+ delete yymsp[-1].minor.yy574;
+ objectForTokens = yygotominor.yy73;
}
break;
case 154: /* selectnowith ::= values */
{
- yygotominor.yy297 = SqliteSelect::append(*(yymsp[0].minor.yy522));
- delete yymsp[0].minor.yy522;
- objectForTokens = yygotominor.yy297;
+ yygotominor.yy73 = SqliteSelect::append(*(yymsp[0].minor.yy54));
+ delete yymsp[0].minor.yy54;
+ objectForTokens = yygotominor.yy73;
}
break;
case 155: /* selectnowith ::= selectnowith COMMA values */
{
- yygotominor.yy297 = SqliteSelect::append(yymsp[-2].minor.yy297, SqliteSelect::CompoundOperator::UNION_ALL, *(yymsp[0].minor.yy522));
- delete yymsp[0].minor.yy522;
- objectForTokens = yygotominor.yy297;
+ yygotominor.yy73 = SqliteSelect::append(yymsp[-2].minor.yy73, SqliteSelect::CompoundOperator::UNION_ALL, *(yymsp[0].minor.yy54));
+ delete yymsp[0].minor.yy54;
+ objectForTokens = yygotominor.yy73;
}
break;
case 156: /* oneselect ::= SELECT distinct selcollist from where_opt groupby_opt having_opt orderby_opt limit_opt */
{
- yygotominor.yy378 = new SqliteSelect::Core(
- *(yymsp[-7].minor.yy130),
- *(yymsp[-6].minor.yy27),
- yymsp[-5].minor.yy553,
- yymsp[-4].minor.yy186,
- *(yymsp[-3].minor.yy615),
- yymsp[-2].minor.yy186,
- *(yymsp[-1].minor.yy226),
- yymsp[0].minor.yy360
+ yygotominor.yy438 = new SqliteSelect::Core(
+ *(yymsp[-7].minor.yy562),
+ *(yymsp[-6].minor.yy421),
+ yymsp[-5].minor.yy335,
+ yymsp[-4].minor.yy176,
+ *(yymsp[-3].minor.yy567),
+ yymsp[-2].minor.yy176,
+ *(yymsp[-1].minor.yy499),
+ yymsp[0].minor.yy4
);
- delete yymsp[-6].minor.yy27;
- delete yymsp[-7].minor.yy130;
- delete yymsp[-3].minor.yy615;
- delete yymsp[-1].minor.yy226;
- objectForTokens = yygotominor.yy378;
+ delete yymsp[-6].minor.yy421;
+ delete yymsp[-7].minor.yy562;
+ delete yymsp[-3].minor.yy567;
+ delete yymsp[-1].minor.yy499;
+ objectForTokens = yygotominor.yy438;
}
break;
case 157: /* oneselect ::= SELECT distinct selcollist from where_opt groupby_opt having_opt window_clause orderby_opt limit_opt */
{
- yygotominor.yy378 = new SqliteSelect::Core(
- *(yymsp[-8].minor.yy130),
- *(yymsp[-7].minor.yy27),
- yymsp[-6].minor.yy553,
- yymsp[-5].minor.yy186,
- *(yymsp[-4].minor.yy615),
- yymsp[-3].minor.yy186,
- *(yymsp[-2].minor.yy525),
- *(yymsp[-1].minor.yy226),
- yymsp[0].minor.yy360
+ yygotominor.yy438 = new SqliteSelect::Core(
+ *(yymsp[-8].minor.yy562),
+ *(yymsp[-7].minor.yy421),
+ yymsp[-6].minor.yy335,
+ yymsp[-5].minor.yy176,
+ *(yymsp[-4].minor.yy567),
+ yymsp[-3].minor.yy176,
+ *(yymsp[-2].minor.yy555),
+ *(yymsp[-1].minor.yy499),
+ yymsp[0].minor.yy4
);
- delete yymsp[-7].minor.yy27;
- delete yymsp[-8].minor.yy130;
- delete yymsp[-4].minor.yy615;
- delete yymsp[-1].minor.yy226;
- delete yymsp[-2].minor.yy525;
- objectForTokens = yygotominor.yy378;
+ delete yymsp[-7].minor.yy421;
+ delete yymsp[-8].minor.yy562;
+ delete yymsp[-4].minor.yy567;
+ delete yymsp[-1].minor.yy499;
+ delete yymsp[-2].minor.yy555;
+ objectForTokens = yygotominor.yy438;
}
break;
case 158: /* values ::= VALUES LP nexprlist RP */
{
- yygotominor.yy522 = new ParserExprNestedList();
- yygotominor.yy522->append(*(yymsp[-1].minor.yy615));
- delete yymsp[-1].minor.yy615;
+ yygotominor.yy54 = new ParserExprNestedList();
+ yygotominor.yy54->append(*(yymsp[-1].minor.yy567));
+ delete yymsp[-1].minor.yy567;
}
break;
case 159: /* values ::= values COMMA LP exprlist RP */
{
- yymsp[-4].minor.yy522->append(*(yymsp[-1].minor.yy615));
- yygotominor.yy522 = yymsp[-4].minor.yy522;
- delete yymsp[-1].minor.yy615;
+ yymsp[-4].minor.yy54->append(*(yymsp[-1].minor.yy567));
+ yygotominor.yy54 = yymsp[-4].minor.yy54;
+ delete yymsp[-1].minor.yy567;
DONT_INHERIT_TOKENS("values");
}
break;
case 160: /* multiselect_op ::= UNION */
-{yygotominor.yy142 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::UNION);}
+{yygotominor.yy574 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::UNION);}
break;
case 161: /* multiselect_op ::= UNION ALL */
-{yygotominor.yy142 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::UNION_ALL);}
+{yygotominor.yy574 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::UNION_ALL);}
break;
case 162: /* multiselect_op ::= EXCEPT */
-{yygotominor.yy142 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::EXCEPT);}
+{yygotominor.yy574 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::EXCEPT);}
break;
case 163: /* multiselect_op ::= INTERSECT */
-{yygotominor.yy142 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::INTERSECT);}
+{yygotominor.yy574 = new SqliteSelect::CompoundOperator(SqliteSelect::CompoundOperator::INTERSECT);}
break;
case 164: /* distinct ::= DISTINCT */
-{yygotominor.yy130 = new int(1);}
+{yygotominor.yy562 = new int(1);}
break;
case 165: /* distinct ::= ALL */
-{yygotominor.yy130 = new int(2);}
+{yygotominor.yy562 = new int(2);}
break;
case 167: /* sclp ::= selcollist COMMA */
-{yygotominor.yy27 = yymsp[-1].minor.yy27;}
+{yygotominor.yy421 = yymsp[-1].minor.yy421;}
break;
case 168: /* sclp ::= */
case 239: /* returning ::= */ yytestcase(yyruleno==239);
-{yygotominor.yy27 = new ParserResultColumnList();}
+{yygotominor.yy421 = new ParserResultColumnList();}
break;
case 169: /* selcollist ::= sclp expr as */
{
SqliteSelect::Core::ResultColumn* obj =
new SqliteSelect::Core::ResultColumn(
- yymsp[-1].minor.yy186,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->asKw : false,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->name : QString()
+ yymsp[-1].minor.yy176,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->asKw : false,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->name : QString()
);
- yymsp[-2].minor.yy27->append(obj);
- yygotominor.yy27 = yymsp[-2].minor.yy27;
- delete yymsp[0].minor.yy628;
+ yymsp[-2].minor.yy421->append(obj);
+ yygotominor.yy421 = yymsp[-2].minor.yy421;
+ delete yymsp[0].minor.yy280;
objectForTokens = obj;
DONT_INHERIT_TOKENS("sclp");
}
@@ -4045,8 +4051,8 @@ static void yy_reduce(
SqliteSelect::Core::ResultColumn* obj =
new SqliteSelect::Core::ResultColumn(true);
- yymsp[-1].minor.yy27->append(obj);
- yygotominor.yy27 = yymsp[-1].minor.yy27;
+ yymsp[-1].minor.yy421->append(obj);
+ yygotominor.yy421 = yymsp[-1].minor.yy421;
objectForTokens = obj;
DONT_INHERIT_TOKENS("sclp");
}
@@ -4056,15 +4062,15 @@ static void yy_reduce(
SqliteSelect::Core::ResultColumn* obj =
new SqliteSelect::Core::ResultColumn(
true,
- yymsp[-2].minor.yy380->toName()
+ yymsp[-2].minor.yy542->toName()
);
- if (!yymsp[-2].minor.yy380->isName())
+ if (!yymsp[-2].minor.yy542->isName())
parserContext->errorAtToken("Syntax error <expected name, not literal value>", -3);
- yymsp[-3].minor.yy27->append(obj);
- yygotominor.yy27 = yymsp[-3].minor.yy27;
- delete yymsp[-2].minor.yy380;
+ yymsp[-3].minor.yy421->append(obj);
+ yygotominor.yy421 = yymsp[-3].minor.yy421;
+ delete yymsp[-2].minor.yy542;
objectForTokens = obj;
DONT_INHERIT_TOKENS("sclp");
}
@@ -4073,378 +4079,378 @@ static void yy_reduce(
case 173: /* selcollist ::= sclp ID_TAB DOT STAR */ yytestcase(yyruleno==173);
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy27 = yymsp[0].minor.yy27;
+ yygotominor.yy421 = yymsp[0].minor.yy421;
}
break;
case 174: /* as ::= AS nm */
{
- yygotominor.yy628 = new ParserStubAlias(*(yymsp[0].minor.yy319), true);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy280 = new ParserStubAlias(*(yymsp[0].minor.yy255), true);
+ delete yymsp[0].minor.yy255;
}
break;
case 175: /* as ::= ids */
case 176: /* as ::= AS ID_ALIAS */ yytestcase(yyruleno==176);
case 177: /* as ::= ID_ALIAS */ yytestcase(yyruleno==177);
{
- yygotominor.yy628 = new ParserStubAlias(*(yymsp[0].minor.yy319), false);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy280 = new ParserStubAlias(*(yymsp[0].minor.yy255), false);
+ delete yymsp[0].minor.yy255;
}
break;
case 178: /* as ::= */
-{yygotominor.yy628 = nullptr;}
+{yygotominor.yy280 = nullptr;}
break;
case 179: /* from ::= */
-{yygotominor.yy553 = nullptr;}
+{yygotominor.yy335 = nullptr;}
break;
case 180: /* from ::= FROM joinsrc */
-{yygotominor.yy553 = yymsp[0].minor.yy553;}
+{yygotominor.yy335 = yymsp[0].minor.yy335;}
break;
case 181: /* joinsrc ::= singlesrc seltablist */
{
- yygotominor.yy553 = new SqliteSelect::Core::JoinSource(
- yymsp[-1].minor.yy595,
- *(yymsp[0].minor.yy107)
+ yygotominor.yy335 = new SqliteSelect::Core::JoinSource(
+ yymsp[-1].minor.yy393,
+ *(yymsp[0].minor.yy195)
);
- delete yymsp[0].minor.yy107;
- objectForTokens = yygotominor.yy553;
+ delete yymsp[0].minor.yy195;
+ objectForTokens = yygotominor.yy335;
}
break;
case 182: /* joinsrc ::= */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy553 = new SqliteSelect::Core::JoinSource();
- objectForTokens = yygotominor.yy553;
+ yygotominor.yy335 = new SqliteSelect::Core::JoinSource();
+ objectForTokens = yygotominor.yy335;
}
break;
case 183: /* seltablist ::= seltablist joinop singlesrc joinconstr_opt */
{
SqliteSelect::Core::JoinSourceOther* src =
- new SqliteSelect::Core::JoinSourceOther(yymsp[-2].minor.yy449, yymsp[-1].minor.yy595, yymsp[0].minor.yy215);
+ new SqliteSelect::Core::JoinSourceOther(yymsp[-2].minor.yy461, yymsp[-1].minor.yy393, yymsp[0].minor.yy423);
- yymsp[-3].minor.yy107->append(src);
- yygotominor.yy107 = yymsp[-3].minor.yy107;
+ yymsp[-3].minor.yy195->append(src);
+ yygotominor.yy195 = yymsp[-3].minor.yy195;
objectForTokens = src;
DONT_INHERIT_TOKENS("seltablist");
}
break;
case 184: /* seltablist ::= */
{
- yygotominor.yy107 = new ParserOtherSourceList();
+ yygotominor.yy195 = new ParserOtherSourceList();
}
break;
case 185: /* singlesrc ::= nm dbnm as indexed_opt */
{
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource(
- *(yymsp[-3].minor.yy319),
- *(yymsp[-2].minor.yy319),
- yymsp[-1].minor.yy628 ? yymsp[-1].minor.yy628->asKw : false,
- yymsp[-1].minor.yy628 ? yymsp[-1].minor.yy628->name : QString(),
- yymsp[0].minor.yy300 ? yymsp[0].minor.yy300->notIndexedKw : false,
- yymsp[0].minor.yy300 ? yymsp[0].minor.yy300->indexedBy : QString()
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource(
+ *(yymsp[-3].minor.yy255),
+ *(yymsp[-2].minor.yy255),
+ yymsp[-1].minor.yy280 ? yymsp[-1].minor.yy280->asKw : false,
+ yymsp[-1].minor.yy280 ? yymsp[-1].minor.yy280->name : QString(),
+ yymsp[0].minor.yy224 ? yymsp[0].minor.yy224->notIndexedKw : false,
+ yymsp[0].minor.yy224 ? yymsp[0].minor.yy224->indexedBy : QString()
);
- delete yymsp[-3].minor.yy319;
- delete yymsp[-2].minor.yy319;
- delete yymsp[-1].minor.yy628;
- if (yymsp[0].minor.yy300)
- delete yymsp[0].minor.yy300;
- objectForTokens = yygotominor.yy595;
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[-1].minor.yy280;
+ if (yymsp[0].minor.yy224)
+ delete yymsp[0].minor.yy224;
+ objectForTokens = yygotominor.yy393;
}
break;
case 186: /* singlesrc ::= LP select RP as */
{
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource(
- yymsp[-2].minor.yy297,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->asKw : false,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->name : QString()
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource(
+ yymsp[-2].minor.yy73,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->asKw : false,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->name : QString()
);
- delete yymsp[0].minor.yy628;
- objectForTokens = yygotominor.yy595;
+ delete yymsp[0].minor.yy280;
+ objectForTokens = yygotominor.yy393;
}
break;
case 187: /* singlesrc ::= LP joinsrc RP as */
{
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource(
- yymsp[-2].minor.yy553,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->asKw : false,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->name : QString()
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource(
+ yymsp[-2].minor.yy335,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->asKw : false,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->name : QString()
);
- delete yymsp[0].minor.yy628;
- objectForTokens = yygotominor.yy595;
+ delete yymsp[0].minor.yy280;
+ objectForTokens = yygotominor.yy393;
}
break;
case 188: /* singlesrc ::= nm dbnm LP exprlist RP as */
{
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource(
- *(yymsp[-5].minor.yy319),
- *(yymsp[-4].minor.yy319),
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->asKw : false,
- yymsp[0].minor.yy628 ? yymsp[0].minor.yy628->name : QString(),
- *(yymsp[-2].minor.yy615)
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource(
+ *(yymsp[-5].minor.yy255),
+ *(yymsp[-4].minor.yy255),
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->asKw : false,
+ yymsp[0].minor.yy280 ? yymsp[0].minor.yy280->name : QString(),
+ *(yymsp[-2].minor.yy567)
);
- delete yymsp[-5].minor.yy319;
- delete yymsp[-4].minor.yy319;
- delete yymsp[0].minor.yy628;
- if (yymsp[-2].minor.yy615)
- delete yymsp[-2].minor.yy615;
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-4].minor.yy255;
+ delete yymsp[0].minor.yy280;
+ if (yymsp[-2].minor.yy567)
+ delete yymsp[-2].minor.yy567;
- objectForTokens = yygotominor.yy595;
+ objectForTokens = yygotominor.yy393;
}
break;
case 189: /* singlesrc ::= */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource();
- objectForTokens = yygotominor.yy595;
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource();
+ objectForTokens = yygotominor.yy393;
}
break;
case 190: /* singlesrc ::= nm DOT */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy595 = new SqliteSelect::Core::SingleSource();
- yygotominor.yy595->database = *(yymsp[-1].minor.yy319);
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy595;
+ yygotominor.yy393 = new SqliteSelect::Core::SingleSource();
+ yygotominor.yy393->database = *(yymsp[-1].minor.yy255);
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy393;
}
break;
case 195: /* joinconstr_opt ::= ON expr */
{
- yygotominor.yy215 = new SqliteSelect::Core::JoinConstraint(yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy215;
+ yygotominor.yy423 = new SqliteSelect::Core::JoinConstraint(yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy423;
}
break;
case 196: /* joinconstr_opt ::= USING LP idlist RP */
{
- yygotominor.yy215 = new SqliteSelect::Core::JoinConstraint(*(yymsp[-1].minor.yy173));
- delete yymsp[-1].minor.yy173;
- objectForTokens = yygotominor.yy215;
+ yygotominor.yy423 = new SqliteSelect::Core::JoinConstraint(*(yymsp[-1].minor.yy336));
+ delete yymsp[-1].minor.yy336;
+ objectForTokens = yygotominor.yy423;
}
break;
case 197: /* joinconstr_opt ::= */
-{yygotominor.yy215 = nullptr;}
+{yygotominor.yy423 = nullptr;}
break;
case 198: /* dbnm ::= */
- case 352: /* collate ::= */ yytestcase(yyruleno==352);
- case 438: /* vtabarg ::= */ yytestcase(yyruleno==438);
- case 442: /* anylist ::= */ yytestcase(yyruleno==442);
-{yygotominor.yy319 = new QString();}
+ case 355: /* collate ::= */ yytestcase(yyruleno==355);
+ case 441: /* vtabarg ::= */ yytestcase(yyruleno==441);
+ case 445: /* anylist ::= */ yytestcase(yyruleno==445);
+{yygotominor.yy255 = new QString();}
break;
case 200: /* fullname ::= nm dbnm */
{
- yygotominor.yy396 = new ParserFullName();
- yygotominor.yy396->name1 = *(yymsp[-1].minor.yy319);
- yygotominor.yy396->name2 = *(yymsp[0].minor.yy319);
- delete yymsp[-1].minor.yy319;
- delete yymsp[0].minor.yy319;
+ yygotominor.yy520 = new ParserFullName();
+ yygotominor.yy520->name1 = *(yymsp[-1].minor.yy255);
+ yygotominor.yy520->name2 = *(yymsp[0].minor.yy255);
+ delete yymsp[-1].minor.yy255;
+ delete yymsp[0].minor.yy255;
}
break;
case 201: /* joinop ::= COMMA */
{
- yygotominor.yy449 = new SqliteSelect::Core::JoinOp(true);
- objectForTokens = yygotominor.yy449;
+ yygotominor.yy461 = new SqliteSelect::Core::JoinOp(true);
+ objectForTokens = yygotominor.yy461;
}
break;
case 202: /* joinop ::= JOIN */
{
- yygotominor.yy449 = new SqliteSelect::Core::JoinOp(false);
- objectForTokens = yygotominor.yy449;
+ yygotominor.yy461 = new SqliteSelect::Core::JoinOp(false);
+ objectForTokens = yygotominor.yy461;
}
break;
case 203: /* joinop ::= JOIN_KW JOIN */
{
- yygotominor.yy449 = new SqliteSelect::Core::JoinOp(yymsp[-1].minor.yy0->value);
- objectForTokens = yygotominor.yy449;
+ yygotominor.yy461 = new SqliteSelect::Core::JoinOp(yymsp[-1].minor.yy0->value);
+ objectForTokens = yygotominor.yy461;
}
break;
case 204: /* joinop ::= JOIN_KW nm JOIN */
{
- yygotominor.yy449 = new SqliteSelect::Core::JoinOp(yymsp[-2].minor.yy0->value, *(yymsp[-1].minor.yy319));
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy449;
+ yygotominor.yy461 = new SqliteSelect::Core::JoinOp(yymsp[-2].minor.yy0->value, *(yymsp[-1].minor.yy255));
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy461;
}
break;
case 205: /* joinop ::= JOIN_KW nm nm JOIN */
case 206: /* joinop ::= ID_JOIN_OPTS */ yytestcase(yyruleno==206);
{
- yygotominor.yy449 = new SqliteSelect::Core::JoinOp(yymsp[-3].minor.yy0->value, *(yymsp[-2].minor.yy319), *(yymsp[-1].minor.yy319));
- delete yymsp[-2].minor.yy319;
- objectForTokens = yygotominor.yy449;
+ yygotominor.yy461 = new SqliteSelect::Core::JoinOp(yymsp[-3].minor.yy0->value, *(yymsp[-2].minor.yy255), *(yymsp[-1].minor.yy255));
+ delete yymsp[-2].minor.yy255;
+ objectForTokens = yygotominor.yy461;
}
break;
case 207: /* indexed_opt ::= */
-{yygotominor.yy300 = nullptr;}
+{yygotominor.yy224 = nullptr;}
break;
case 208: /* indexed_opt ::= INDEXED BY nm */
{
- yygotominor.yy300 = new ParserIndexedBy(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
+ yygotominor.yy224 = new ParserIndexedBy(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
}
break;
case 209: /* indexed_opt ::= NOT INDEXED */
case 210: /* indexed_opt ::= INDEXED BY ID_IDX */ yytestcase(yyruleno==210);
-{yygotominor.yy300 = new ParserIndexedBy(true);}
+{yygotominor.yy224 = new ParserIndexedBy(true);}
break;
case 211: /* orderby_opt ::= */
-{yygotominor.yy226 = new ParserOrderByList();}
+{yygotominor.yy499 = new ParserOrderByList();}
break;
case 212: /* orderby_opt ::= ORDER BY sortlist */
-{yygotominor.yy226 = yymsp[0].minor.yy226;}
+{yygotominor.yy499 = yymsp[0].minor.yy499;}
break;
case 213: /* sortlist ::= sortlist COMMA expr sortorder nulls */
{
- SqliteOrderBy* obj = new SqliteOrderBy(yymsp[-2].minor.yy186, *(yymsp[-1].minor.yy35), *(yymsp[0].minor.yy315));
- yymsp[-4].minor.yy226->append(obj);
- yygotominor.yy226 = yymsp[-4].minor.yy226;
- delete yymsp[-1].minor.yy35;
- delete yymsp[0].minor.yy315;
+ SqliteOrderBy* obj = new SqliteOrderBy(yymsp[-2].minor.yy176, *(yymsp[-1].minor.yy645), *(yymsp[0].minor.yy99));
+ yymsp[-4].minor.yy499->append(obj);
+ yygotominor.yy499 = yymsp[-4].minor.yy499;
+ delete yymsp[-1].minor.yy645;
+ delete yymsp[0].minor.yy99;
objectForTokens = obj;
DONT_INHERIT_TOKENS("sortlist");
}
break;
case 214: /* sortlist ::= expr sortorder nulls */
{
- SqliteOrderBy* obj = new SqliteOrderBy(yymsp[-2].minor.yy186, *(yymsp[-1].minor.yy35), *(yymsp[0].minor.yy315));
- yygotominor.yy226 = new ParserOrderByList();
- yygotominor.yy226->append(obj);
- delete yymsp[-1].minor.yy35;
- delete yymsp[0].minor.yy315;
+ SqliteOrderBy* obj = new SqliteOrderBy(yymsp[-2].minor.yy176, *(yymsp[-1].minor.yy645), *(yymsp[0].minor.yy99));
+ yygotominor.yy499 = new ParserOrderByList();
+ yygotominor.yy499->append(obj);
+ delete yymsp[-1].minor.yy645;
+ delete yymsp[0].minor.yy99;
objectForTokens = obj;
}
break;
case 215: /* sortorder ::= ASC */
-{yygotominor.yy35 = new SqliteSortOrder(SqliteSortOrder::ASC);}
+{yygotominor.yy645 = new SqliteSortOrder(SqliteSortOrder::ASC);}
break;
case 216: /* sortorder ::= DESC */
-{yygotominor.yy35 = new SqliteSortOrder(SqliteSortOrder::DESC);}
+{yygotominor.yy645 = new SqliteSortOrder(SqliteSortOrder::DESC);}
break;
case 217: /* sortorder ::= */
-{yygotominor.yy35 = new SqliteSortOrder(SqliteSortOrder::null);}
+{yygotominor.yy645 = new SqliteSortOrder(SqliteSortOrder::null);}
break;
case 218: /* nulls ::= NULLS FIRST */
-{yygotominor.yy315 = new SqliteNulls(SqliteNulls::FIRST);}
+{yygotominor.yy99 = new SqliteNulls(SqliteNulls::FIRST);}
break;
case 219: /* nulls ::= NULLS LAST */
-{yygotominor.yy315 = new SqliteNulls(SqliteNulls::LAST);}
+{yygotominor.yy99 = new SqliteNulls(SqliteNulls::LAST);}
break;
case 220: /* nulls ::= */
-{yygotominor.yy315 = new SqliteNulls(SqliteNulls::null);}
+{yygotominor.yy99 = new SqliteNulls(SqliteNulls::null);}
break;
case 221: /* groupby_opt ::= */
- case 337: /* exprlist ::= */ yytestcase(yyruleno==337);
-{yygotominor.yy615 = new ParserExprList();}
+ case 340: /* exprlist ::= */ yytestcase(yyruleno==340);
+{yygotominor.yy567 = new ParserExprList();}
break;
case 222: /* groupby_opt ::= GROUP BY nexprlist */
- case 336: /* exprlist ::= nexprlist */ yytestcase(yyruleno==336);
-{yygotominor.yy615 = yymsp[0].minor.yy615;}
+ case 339: /* exprlist ::= nexprlist */ yytestcase(yyruleno==339);
+{yygotominor.yy567 = yymsp[0].minor.yy567;}
break;
case 223: /* groupby_opt ::= GROUP BY */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy615 = new ParserExprList();
+ yygotominor.yy567 = new ParserExprList();
}
break;
case 224: /* having_opt ::= */
case 236: /* where_opt ::= */ yytestcase(yyruleno==236);
- case 333: /* case_else ::= */ yytestcase(yyruleno==333);
- case 335: /* case_operand ::= */ yytestcase(yyruleno==335);
- case 361: /* vinto ::= */ yytestcase(yyruleno==361);
- case 395: /* when_clause ::= */ yytestcase(yyruleno==395);
- case 410: /* key_opt ::= */ yytestcase(yyruleno==410);
-{yygotominor.yy186 = nullptr;}
+ case 336: /* case_else ::= */ yytestcase(yyruleno==336);
+ case 338: /* case_operand ::= */ yytestcase(yyruleno==338);
+ case 364: /* vinto ::= */ yytestcase(yyruleno==364);
+ case 398: /* when_clause ::= */ yytestcase(yyruleno==398);
+ case 413: /* key_opt ::= */ yytestcase(yyruleno==413);
+{yygotominor.yy176 = nullptr;}
break;
case 225: /* having_opt ::= HAVING expr */
case 237: /* where_opt ::= WHERE expr */ yytestcase(yyruleno==237);
- case 326: /* expr ::= exprx */ yytestcase(yyruleno==326);
- case 332: /* case_else ::= ELSE expr */ yytestcase(yyruleno==332);
- case 334: /* case_operand ::= exprx */ yytestcase(yyruleno==334);
- case 360: /* vinto ::= INTO expr */ yytestcase(yyruleno==360);
- case 396: /* when_clause ::= WHEN expr */ yytestcase(yyruleno==396);
- case 411: /* key_opt ::= KEY expr */ yytestcase(yyruleno==411);
-{yygotominor.yy186 = yymsp[0].minor.yy186;}
+ case 327: /* expr ::= exprx */ yytestcase(yyruleno==327);
+ case 335: /* case_else ::= ELSE expr */ yytestcase(yyruleno==335);
+ case 337: /* case_operand ::= exprx */ yytestcase(yyruleno==337);
+ case 363: /* vinto ::= INTO expr */ yytestcase(yyruleno==363);
+ case 399: /* when_clause ::= WHEN expr */ yytestcase(yyruleno==399);
+ case 414: /* key_opt ::= KEY expr */ yytestcase(yyruleno==414);
+{yygotominor.yy176 = yymsp[0].minor.yy176;}
break;
case 226: /* limit_opt ::= */
-{yygotominor.yy360 = nullptr;}
+{yygotominor.yy4 = nullptr;}
break;
case 227: /* limit_opt ::= LIMIT expr */
{
- yygotominor.yy360 = new SqliteLimit(yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy360;
+ yygotominor.yy4 = new SqliteLimit(yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy4;
}
break;
case 228: /* limit_opt ::= LIMIT expr OFFSET expr */
{
- yygotominor.yy360 = new SqliteLimit(yymsp[-2].minor.yy186, yymsp[0].minor.yy186, true);
- objectForTokens = yygotominor.yy360;
+ yygotominor.yy4 = new SqliteLimit(yymsp[-2].minor.yy176, yymsp[0].minor.yy176, true);
+ objectForTokens = yygotominor.yy4;
}
break;
case 229: /* limit_opt ::= LIMIT expr COMMA expr */
{
- yygotominor.yy360 = new SqliteLimit(yymsp[-2].minor.yy186, yymsp[0].minor.yy186, false);
- objectForTokens = yygotominor.yy360;
+ yygotominor.yy4 = new SqliteLimit(yymsp[-2].minor.yy176, yymsp[0].minor.yy176, false);
+ objectForTokens = yygotominor.yy4;
}
break;
case 231: /* delete_stmt ::= with DELETE FROM fullname indexed_opt where_opt returning */
{
- if (yymsp[-2].minor.yy300)
+ if (yymsp[-2].minor.yy224)
{
- if (!yymsp[-2].minor.yy300->indexedBy.isNull())
+ if (!yymsp[-2].minor.yy224->indexedBy.isNull())
{
- yygotominor.yy41 = new SqliteDelete(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
- yymsp[-2].minor.yy300->indexedBy,
- yymsp[-1].minor.yy186,
- yymsp[-6].minor.yy161,
- *(yymsp[0].minor.yy27)
+ yygotominor.yy635 = new SqliteDelete(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ yymsp[-2].minor.yy224->indexedBy,
+ yymsp[-1].minor.yy176,
+ yymsp[-6].minor.yy321,
+ *(yymsp[0].minor.yy421)
);
}
else
{
- yygotominor.yy41 = new SqliteDelete(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
- yymsp[-2].minor.yy300->notIndexedKw,
- yymsp[-1].minor.yy186,
- yymsp[-6].minor.yy161,
- *(yymsp[0].minor.yy27)
+ yygotominor.yy635 = new SqliteDelete(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ yymsp[-2].minor.yy224->notIndexedKw,
+ yymsp[-1].minor.yy176,
+ yymsp[-6].minor.yy321,
+ *(yymsp[0].minor.yy421)
);
}
- delete yymsp[-2].minor.yy300;
+ delete yymsp[-2].minor.yy224;
}
else
{
- yygotominor.yy41 = new SqliteDelete(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
+ yygotominor.yy635 = new SqliteDelete(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
false,
- yymsp[-1].minor.yy186,
- yymsp[-6].minor.yy161,
- *(yymsp[0].minor.yy27)
+ yymsp[-1].minor.yy176,
+ yymsp[-6].minor.yy321,
+ *(yymsp[0].minor.yy421)
);
}
- delete yymsp[-3].minor.yy396;
- delete yymsp[0].minor.yy27;
+ delete yymsp[-3].minor.yy520;
+ delete yymsp[0].minor.yy421;
// since it's used in trigger:
- objectForTokens = yygotominor.yy41;
+ objectForTokens = yygotominor.yy635;
}
break;
case 232: /* delete_stmt ::= with DELETE FROM */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteDelete* q = new SqliteDelete();
- q->with = yymsp[-2].minor.yy161;
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
+ q->with = yymsp[-2].minor.yy321;
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
}
break;
case 233: /* delete_stmt ::= with DELETE FROM nm DOT */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteDelete* q = new SqliteDelete();
- q->with = yymsp[-4].minor.yy161;
- q->database = *(yymsp[-1].minor.yy319);
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
- delete yymsp[-1].minor.yy319;
+ q->with = yymsp[-4].minor.yy321;
+ q->database = *(yymsp[-1].minor.yy255);
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[-1].minor.yy255;
}
break;
case 234: /* delete_stmt ::= with DELETE FROM nm DOT ID_TAB */
@@ -4461,96 +4467,96 @@ static void yy_reduce(
case 238: /* where_opt ::= WHERE */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy186 = new SqliteExpr();
+ yygotominor.yy176 = new SqliteExpr();
}
break;
case 240: /* returning ::= RETURNING selcollist */
-{yygotominor.yy27 = yymsp[0].minor.yy27;}
+{yygotominor.yy421 = yymsp[0].minor.yy421;}
break;
case 242: /* update_stmt ::= with UPDATE orconf fullname indexed_opt SET setlist from where_opt returning */
{
- yygotominor.yy41 = new SqliteUpdate(
- *(yymsp[-7].minor.yy136),
- yymsp[-6].minor.yy396->name1,
- yymsp[-6].minor.yy396->name2,
- yymsp[-5].minor.yy300 ? yymsp[-5].minor.yy300->notIndexedKw : false,
- yymsp[-5].minor.yy300 ? yymsp[-5].minor.yy300->indexedBy : QString(),
- *(yymsp[-3].minor.yy621),
- yymsp[-2].minor.yy553,
- yymsp[-1].minor.yy186,
- yymsp[-9].minor.yy161,
- *(yymsp[0].minor.yy27)
+ yygotominor.yy635 = new SqliteUpdate(
+ *(yymsp[-7].minor.yy66),
+ yymsp[-6].minor.yy520->name1,
+ yymsp[-6].minor.yy520->name2,
+ yymsp[-5].minor.yy224 ? yymsp[-5].minor.yy224->notIndexedKw : false,
+ yymsp[-5].minor.yy224 ? yymsp[-5].minor.yy224->indexedBy : QString(),
+ *(yymsp[-3].minor.yy617),
+ yymsp[-2].minor.yy335,
+ yymsp[-1].minor.yy176,
+ yymsp[-9].minor.yy321,
+ *(yymsp[0].minor.yy421)
);
- delete yymsp[-7].minor.yy136;
- delete yymsp[-6].minor.yy396;
- delete yymsp[-3].minor.yy621;
- delete yymsp[0].minor.yy27;
- if (yymsp[-5].minor.yy300)
- delete yymsp[-5].minor.yy300;
+ delete yymsp[-7].minor.yy66;
+ delete yymsp[-6].minor.yy520;
+ delete yymsp[-3].minor.yy617;
+ delete yymsp[0].minor.yy421;
+ if (yymsp[-5].minor.yy224)
+ delete yymsp[-5].minor.yy224;
// since it's used in trigger:
- objectForTokens = yygotominor.yy41;
+ objectForTokens = yygotominor.yy635;
}
break;
case 243: /* update_stmt ::= with UPDATE orconf */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteUpdate* q = new SqliteUpdate();
- q->with = yymsp[-2].minor.yy161;
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
- delete yymsp[0].minor.yy136;
+ q->with = yymsp[-2].minor.yy321;
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[0].minor.yy66;
}
break;
case 244: /* update_stmt ::= with UPDATE orconf nm DOT */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteUpdate* q = new SqliteUpdate();
- q->with = yymsp[-4].minor.yy161;
- q->database = *(yymsp[-1].minor.yy319);
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
- delete yymsp[-2].minor.yy136;
- delete yymsp[-1].minor.yy319;
+ q->with = yymsp[-4].minor.yy321;
+ q->database = *(yymsp[-1].minor.yy255);
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[-2].minor.yy66;
+ delete yymsp[-1].minor.yy255;
}
break;
case 247: /* setlist ::= setlist COMMA nm EQ expr */
{
- yymsp[-4].minor.yy621->append(ParserSetValue(*(yymsp[-2].minor.yy319), yymsp[0].minor.yy186));
- yygotominor.yy621 = yymsp[-4].minor.yy621;
- delete yymsp[-2].minor.yy319;
+ yymsp[-4].minor.yy617->append(ParserSetValue(*(yymsp[-2].minor.yy255), yymsp[0].minor.yy176));
+ yygotominor.yy617 = yymsp[-4].minor.yy617;
+ delete yymsp[-2].minor.yy255;
}
break;
case 248: /* setlist ::= setlist COMMA LP idlist RP EQ expr */
{
- yymsp[-6].minor.yy621->append(ParserSetValue(*(yymsp[-3].minor.yy173), yymsp[0].minor.yy186));
- yygotominor.yy621 = yymsp[-6].minor.yy621;
- delete yymsp[-3].minor.yy173;
+ yymsp[-6].minor.yy617->append(ParserSetValue(*(yymsp[-3].minor.yy336), yymsp[0].minor.yy176));
+ yygotominor.yy617 = yymsp[-6].minor.yy617;
+ delete yymsp[-3].minor.yy336;
}
break;
case 249: /* setlist ::= nm EQ expr */
{
- yygotominor.yy621 = new ParserSetValueList();
- yygotominor.yy621->append(ParserSetValue(*(yymsp[-2].minor.yy319), yymsp[0].minor.yy186));
- delete yymsp[-2].minor.yy319;
+ yygotominor.yy617 = new ParserSetValueList();
+ yygotominor.yy617->append(ParserSetValue(*(yymsp[-2].minor.yy255), yymsp[0].minor.yy176));
+ delete yymsp[-2].minor.yy255;
}
break;
case 250: /* setlist ::= LP idlist RP EQ expr */
{
- yygotominor.yy621 = new ParserSetValueList();
- yygotominor.yy621->append(ParserSetValue(*(yymsp[-3].minor.yy173), yymsp[0].minor.yy186));
- delete yymsp[-3].minor.yy173;
+ yygotominor.yy617 = new ParserSetValueList();
+ yygotominor.yy617->append(ParserSetValue(*(yymsp[-3].minor.yy336), yymsp[0].minor.yy176));
+ delete yymsp[-3].minor.yy336;
}
break;
case 251: /* setlist ::= */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy621 = new ParserSetValueList();
+ yygotominor.yy617 = new ParserSetValueList();
}
break;
case 252: /* setlist ::= setlist COMMA */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy621 = yymsp[-1].minor.yy621;
+ yygotominor.yy617 = yymsp[-1].minor.yy617;
}
break;
case 253: /* setlist ::= setlist COMMA ID_COL */
@@ -4559,29 +4565,29 @@ static void yy_reduce(
}
break;
case 255: /* idlist_opt ::= */
-{yygotominor.yy173 = new QStringList();}
+{yygotominor.yy336 = new QStringList();}
break;
case 256: /* idlist_opt ::= LP idlist RP */
-{yygotominor.yy173 = yymsp[-1].minor.yy173;}
+{yygotominor.yy336 = yymsp[-1].minor.yy336;}
break;
case 257: /* idlist ::= idlist COMMA nm */
{
- yygotominor.yy173 = yymsp[-2].minor.yy173;
- *(yygotominor.yy173) << *(yymsp[0].minor.yy319);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy336 = yymsp[-2].minor.yy336;
+ *(yygotominor.yy336) << *(yymsp[0].minor.yy255);
+ delete yymsp[0].minor.yy255;
}
break;
case 258: /* idlist ::= nm */
{
- yygotominor.yy173 = new QStringList();
- *(yygotominor.yy173) << *(yymsp[0].minor.yy319);
- delete yymsp[0].minor.yy319;
+ yygotominor.yy336 = new QStringList();
+ *(yygotominor.yy336) << *(yymsp[0].minor.yy255);
+ delete yymsp[0].minor.yy255;
}
break;
case 259: /* idlist ::= */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
- yygotominor.yy173 = new QStringList();
+ yygotominor.yy336 = new QStringList();
}
break;
case 260: /* idlist ::= idlist COMMA ID_COL */
@@ -4591,1211 +4597,1230 @@ static void yy_reduce(
break;
case 263: /* insert_stmt ::= with insert_cmd INTO fullname idlist_opt select upsert returning */
{
- yygotominor.yy41 = new SqliteInsert(
- yymsp[-6].minor.yy308->replace,
- yymsp[-6].minor.yy308->orConflict,
- yymsp[-4].minor.yy396->name1,
- yymsp[-4].minor.yy396->name2,
- *(yymsp[-3].minor.yy173),
- yymsp[-2].minor.yy297,
- yymsp[-7].minor.yy161,
- yymsp[-1].minor.yy332,
- *(yymsp[0].minor.yy27)
+ yygotominor.yy635 = new SqliteInsert(
+ yymsp[-6].minor.yy281->replace,
+ yymsp[-6].minor.yy281->orConflict,
+ yymsp[-4].minor.yy520->name1,
+ yymsp[-4].minor.yy520->name2,
+ *(yymsp[-3].minor.yy336),
+ yymsp[-2].minor.yy73,
+ yymsp[-7].minor.yy321,
+ yymsp[-1].minor.yy16,
+ *(yymsp[0].minor.yy421)
);
- delete yymsp[-4].minor.yy396;
- delete yymsp[-6].minor.yy308;
- delete yymsp[-3].minor.yy173;
- delete yymsp[0].minor.yy27;
+ delete yymsp[-4].minor.yy520;
+ delete yymsp[-6].minor.yy281;
+ delete yymsp[-3].minor.yy336;
+ delete yymsp[0].minor.yy421;
// since it's used in trigger:
- objectForTokens = yygotominor.yy41;
+ objectForTokens = yygotominor.yy635;
}
break;
case 264: /* insert_stmt ::= with insert_cmd INTO fullname idlist_opt DEFAULT VALUES returning */
{
- yygotominor.yy41 = new SqliteInsert(
- yymsp[-6].minor.yy308->replace,
- yymsp[-6].minor.yy308->orConflict,
- yymsp[-4].minor.yy396->name1,
- yymsp[-4].minor.yy396->name2,
- *(yymsp[-3].minor.yy173),
- yymsp[-7].minor.yy161,
- *(yymsp[0].minor.yy27)
+ yygotominor.yy635 = new SqliteInsert(
+ yymsp[-6].minor.yy281->replace,
+ yymsp[-6].minor.yy281->orConflict,
+ yymsp[-4].minor.yy520->name1,
+ yymsp[-4].minor.yy520->name2,
+ *(yymsp[-3].minor.yy336),
+ yymsp[-7].minor.yy321,
+ *(yymsp[0].minor.yy421)
);
- delete yymsp[-4].minor.yy396;
- delete yymsp[-6].minor.yy308;
- delete yymsp[-3].minor.yy173;
- delete yymsp[0].minor.yy27;
+ delete yymsp[-4].minor.yy520;
+ delete yymsp[-6].minor.yy281;
+ delete yymsp[-3].minor.yy336;
+ delete yymsp[0].minor.yy421;
// since it's used in trigger:
- objectForTokens = yygotominor.yy41;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 265: /* insert_stmt ::= with insert_cmd INTO */
+ case 265: /* insert_stmt ::= with insert_cmd INTO fullname LP idlist rp_opt */
+{
+ parserContext->minorErrorBeforeNextToken("Syntax error");
+ yygotominor.yy635 = new SqliteInsert(
+ yymsp[-5].minor.yy281->replace,
+ yymsp[-5].minor.yy281->orConflict,
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ *(yymsp[-1].minor.yy336),
+ yymsp[-6].minor.yy321,
+ QList<SqliteResultColumn*>()
+ );
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[-3].minor.yy520;
+ delete yymsp[-1].minor.yy336;
+ delete yymsp[-5].minor.yy281;
+ delete yymsp[0].minor.yy35;
+ }
+ break;
+ case 266: /* insert_stmt ::= with insert_cmd INTO */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteInsert* q = new SqliteInsert();
- q->replaceKw = yymsp[-1].minor.yy308->replace;
- q->onConflict = yymsp[-1].minor.yy308->orConflict;
- q->with = yymsp[-2].minor.yy161;
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
- delete yymsp[-1].minor.yy308;
+ q->replaceKw = yymsp[-1].minor.yy281->replace;
+ q->onConflict = yymsp[-1].minor.yy281->orConflict;
+ q->with = yymsp[-2].minor.yy321;
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[-1].minor.yy281;
}
break;
- case 266: /* insert_stmt ::= with insert_cmd INTO nm DOT */
+ case 267: /* insert_stmt ::= with insert_cmd INTO nm DOT */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
SqliteInsert* q = new SqliteInsert();
- q->replaceKw = yymsp[-3].minor.yy308->replace;
- q->onConflict = yymsp[-3].minor.yy308->orConflict;
- q->with = yymsp[-4].minor.yy161;
- q->database = *(yymsp[-1].minor.yy319);
- yygotominor.yy41 = q;
- objectForTokens = yygotominor.yy41;
- delete yymsp[-3].minor.yy308;
- delete yymsp[-1].minor.yy319;
+ q->replaceKw = yymsp[-3].minor.yy281->replace;
+ q->onConflict = yymsp[-3].minor.yy281->orConflict;
+ q->with = yymsp[-4].minor.yy321;
+ q->database = *(yymsp[-1].minor.yy255);
+ yygotominor.yy635 = q;
+ objectForTokens = yygotominor.yy635;
+ delete yymsp[-3].minor.yy281;
+ delete yymsp[-1].minor.yy255;
}
break;
- case 267: /* insert_stmt ::= with insert_cmd INTO ID_DB|ID_TAB */
+ case 268: /* insert_stmt ::= with insert_cmd INTO ID_DB|ID_TAB */
{ yy_destructor(yypParser,249,&yymsp[-3].minor);
yy_destructor(yypParser,283,&yymsp[-2].minor);
}
break;
- case 268: /* insert_stmt ::= with insert_cmd INTO nm DOT ID_TAB */
+ case 269: /* insert_stmt ::= with insert_cmd INTO nm DOT ID_TAB */
{ yy_destructor(yypParser,249,&yymsp[-5].minor);
yy_destructor(yypParser,283,&yymsp[-4].minor);
yy_destructor(yypParser,203,&yymsp[-2].minor);
}
break;
- case 269: /* insert_cmd ::= INSERT orconf */
+ case 270: /* insert_cmd ::= INSERT orconf */
{
- yygotominor.yy308 = new ParserStubInsertOrReplace(false, *(yymsp[0].minor.yy136));
- delete yymsp[0].minor.yy136;
+ yygotominor.yy281 = new ParserStubInsertOrReplace(false, *(yymsp[0].minor.yy66));
+ delete yymsp[0].minor.yy66;
}
break;
- case 270: /* insert_cmd ::= REPLACE */
-{yygotominor.yy308 = new ParserStubInsertOrReplace(true);}
+ case 271: /* insert_cmd ::= REPLACE */
+{yygotominor.yy281 = new ParserStubInsertOrReplace(true);}
break;
- case 271: /* upsert ::= */
+ case 272: /* upsert ::= */
{
- yygotominor.yy332 = nullptr;
+ yygotominor.yy16 = nullptr;
}
break;
- case 272: /* upsert ::= ON CONFLICT LP sortlist RP where_opt DO UPDATE SET setlist where_opt */
+ case 273: /* upsert ::= ON CONFLICT LP sortlist RP where_opt DO UPDATE SET setlist where_opt */
{
- yygotominor.yy332 = new SqliteUpsert(*(yymsp[-7].minor.yy226), yymsp[-5].minor.yy186, *(yymsp[-1].minor.yy621), yymsp[0].minor.yy186);
- delete yymsp[-7].minor.yy226;
- delete yymsp[-1].minor.yy621;
- objectForTokens = yygotominor.yy332;
+ yygotominor.yy16 = new SqliteUpsert(*(yymsp[-7].minor.yy499), yymsp[-5].minor.yy176, *(yymsp[-1].minor.yy617), yymsp[0].minor.yy176);
+ delete yymsp[-7].minor.yy499;
+ delete yymsp[-1].minor.yy617;
+ objectForTokens = yygotominor.yy16;
}
break;
- case 273: /* upsert ::= ON CONFLICT LP sortlist RP where_opt DO NOTHING */
+ case 274: /* upsert ::= ON CONFLICT LP sortlist RP where_opt DO NOTHING */
{
- yygotominor.yy332 = new SqliteUpsert(*(yymsp[-4].minor.yy226), yymsp[-2].minor.yy186);
- delete yymsp[-4].minor.yy226;
- objectForTokens = yygotominor.yy332;
+ yygotominor.yy16 = new SqliteUpsert(*(yymsp[-4].minor.yy499), yymsp[-2].minor.yy176);
+ delete yymsp[-4].minor.yy499;
+ objectForTokens = yygotominor.yy16;
}
break;
- case 274: /* upsert ::= ON CONFLICT DO NOTHING */
+ case 275: /* upsert ::= ON CONFLICT DO NOTHING */
{
- yygotominor.yy332 = new SqliteUpsert();
- objectForTokens = yygotominor.yy332;
+ yygotominor.yy16 = new SqliteUpsert();
+ objectForTokens = yygotominor.yy16;
}
break;
- case 275: /* exprx ::= expr not_opt IN ID_DB */
+ case 276: /* exprx ::= expr not_opt IN ID_DB */
{ yy_destructor(yypParser,227,&yymsp[-3].minor);
}
break;
- case 276: /* exprx ::= expr not_opt IN nm DOT ID_TAB */
- case 277: /* exprx ::= ID_DB|ID_TAB|ID_COL|ID_FN */ yytestcase(yyruleno==277);
+ case 277: /* exprx ::= expr not_opt IN nm DOT ID_TAB */
+ case 278: /* exprx ::= ID_DB|ID_TAB|ID_COL|ID_FN */ yytestcase(yyruleno==278);
{ yy_destructor(yypParser,227,&yymsp[-5].minor);
yy_destructor(yypParser,203,&yymsp[-2].minor);
}
break;
- case 278: /* exprx ::= tnm DOT ID_TAB|ID_COL */
+ case 279: /* exprx ::= tnm DOT ID_TAB|ID_COL */
{ yy_destructor(yypParser,235,&yymsp[-2].minor);
}
break;
- case 279: /* exprx ::= tnm DOT nm DOT ID_COL */
+ case 280: /* exprx ::= tnm DOT nm DOT ID_COL */
{ yy_destructor(yypParser,235,&yymsp[-4].minor);
yy_destructor(yypParser,203,&yymsp[-2].minor);
}
break;
- case 280: /* exprx ::= expr COLLATE ID_COLLATE */
- case 281: /* exprx ::= RAISE LP raisetype COMMA ID_ERR_MSG RP */ yytestcase(yyruleno==281);
+ case 281: /* exprx ::= expr COLLATE ID_COLLATE */
+ case 282: /* exprx ::= RAISE LP raisetype COMMA ID_ERR_MSG RP */ yytestcase(yyruleno==282);
{ yy_destructor(yypParser,227,&yymsp[-2].minor);
}
break;
- case 282: /* exprx ::= CTIME_KW */
+ case 283: /* exprx ::= CTIME_KW */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initCTime(yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initCTime(yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 283: /* exprx ::= LP nexprlist RP */
+ case 284: /* exprx ::= LP nexprlist RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initRowValue(*(yymsp[-1].minor.yy615));
- delete yymsp[-1].minor.yy615;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initRowValue(*(yymsp[-1].minor.yy567));
+ delete yymsp[-1].minor.yy567;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 284: /* exprx ::= tnm */
+ case 285: /* exprx ::= tnm */
{
- yygotominor.yy186 = new SqliteExpr();
- if (yymsp[0].minor.yy380->isLiteral())
- yygotominor.yy186->initLiteral(yymsp[0].minor.yy380->toLiteral());
+ yygotominor.yy176 = new SqliteExpr();
+ if (yymsp[0].minor.yy542->isLiteral())
+ yygotominor.yy176->initLiteral(yymsp[0].minor.yy542->toLiteral());
else
- yygotominor.yy186->initId(yymsp[0].minor.yy380->toName());
+ yygotominor.yy176->initId(yymsp[0].minor.yy542->toName());
//parserContext->errorBeforeLastToken("Syntax error <expected literal value>");
- delete yymsp[0].minor.yy380;
- objectForTokens = yygotominor.yy186;
+ delete yymsp[0].minor.yy542;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 285: /* exprx ::= tnm DOT nm */
+ case 286: /* exprx ::= tnm DOT nm */
{
- yygotominor.yy186 = new SqliteExpr();
- if (yymsp[-2].minor.yy380->isName())
- yygotominor.yy186->initId(yymsp[-2].minor.yy380->toName(), *(yymsp[0].minor.yy319));
+ yygotominor.yy176 = new SqliteExpr();
+ if (yymsp[-2].minor.yy542->isName())
+ yygotominor.yy176->initId(yymsp[-2].minor.yy542->toName(), *(yymsp[0].minor.yy255));
else
parserContext->errorAtToken("Syntax error <expected name>", -3);
- delete yymsp[-2].minor.yy380;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy186;
+ delete yymsp[-2].minor.yy542;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 286: /* exprx ::= tnm DOT */
+ case 287: /* exprx ::= tnm DOT */
{
- yygotominor.yy186 = new SqliteExpr();
- objectForTokens = yygotominor.yy186;
- if (yymsp[-1].minor.yy380->isName())
+ yygotominor.yy176 = new SqliteExpr();
+ objectForTokens = yygotominor.yy176;
+ if (yymsp[-1].minor.yy542->isName())
{
- yygotominor.yy186->initId(yymsp[-1].minor.yy380->toName(), QString());
+ yygotominor.yy176->initId(yymsp[-1].minor.yy542->toName(), QString());
parserContext->minorErrorAfterLastToken("Syntax error <expr>");
}
else
parserContext->errorAtToken("Syntax error <expected name>", -3);
- delete yymsp[-1].minor.yy380;
+ delete yymsp[-1].minor.yy542;
}
break;
- case 287: /* exprx ::= tnm DOT nm DOT nm */
+ case 288: /* exprx ::= tnm DOT nm DOT nm */
{
- yygotominor.yy186 = new SqliteExpr();
- if (yymsp[-4].minor.yy380->isName())
- yygotominor.yy186->initId(yymsp[-4].minor.yy380->toName(), *(yymsp[-2].minor.yy319), *(yymsp[0].minor.yy319));
+ yygotominor.yy176 = new SqliteExpr();
+ if (yymsp[-4].minor.yy542->isName())
+ yygotominor.yy176->initId(yymsp[-4].minor.yy542->toName(), *(yymsp[-2].minor.yy255), *(yymsp[0].minor.yy255));
else
parserContext->errorAtToken("Syntax error <expected name>", -5);
- delete yymsp[-4].minor.yy380;
- delete yymsp[-2].minor.yy319;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy186;
+ delete yymsp[-4].minor.yy542;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 288: /* exprx ::= tnm DOT nm DOT */
+ case 289: /* exprx ::= tnm DOT nm DOT */
{
- yygotominor.yy186 = new SqliteExpr();
- objectForTokens = yygotominor.yy186;
- if (yymsp[-3].minor.yy380->isName())
+ yygotominor.yy176 = new SqliteExpr();
+ objectForTokens = yygotominor.yy176;
+ if (yymsp[-3].minor.yy542->isName())
{
- yygotominor.yy186->initId(yymsp[-3].minor.yy380->toName(), *(yymsp[-1].minor.yy319), QString());
+ yygotominor.yy176->initId(yymsp[-3].minor.yy542->toName(), *(yymsp[-1].minor.yy255), QString());
parserContext->minorErrorAfterLastToken("Syntax error <expr>");
}
else
parserContext->errorAtToken("Syntax error <expected name>", -5);
- delete yymsp[-3].minor.yy380;
- delete yymsp[-1].minor.yy319;
+ delete yymsp[-3].minor.yy542;
+ delete yymsp[-1].minor.yy255;
}
break;
- case 289: /* exprx ::= VARIABLE */
+ case 290: /* exprx ::= VARIABLE */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initBindParam(yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initBindParam(yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 290: /* exprx ::= expr COLLATE ids */
+ case 291: /* exprx ::= expr COLLATE ids */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initCollate(yymsp[-2].minor.yy186, *(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initCollate(yymsp[-2].minor.yy176, *(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 291: /* exprx ::= CAST LP expr AS typetoken RP */
+ case 292: /* exprx ::= CAST LP expr AS typetoken RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initCast(yymsp[-3].minor.yy186, yymsp[-1].minor.yy267);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initCast(yymsp[-3].minor.yy176, yymsp[-1].minor.yy601);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 292: /* exprx ::= ID LP distinct exprlist RP */
+ case 293: /* exprx ::= ID LP distinct exprlist RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initFunction(stripObjName(yymsp[-4].minor.yy0->value), *(yymsp[-2].minor.yy130), *(yymsp[-1].minor.yy615));
- delete yymsp[-2].minor.yy130;
- delete yymsp[-1].minor.yy615;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initFunction(stripObjName(yymsp[-4].minor.yy0->value), *(yymsp[-2].minor.yy562), *(yymsp[-1].minor.yy567));
+ delete yymsp[-2].minor.yy562;
+ delete yymsp[-1].minor.yy567;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 293: /* exprx ::= ID LP STAR RP */
+ case 294: /* exprx ::= ID LP STAR RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initFunction(stripObjName(yymsp[-3].minor.yy0->value), true);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initFunction(stripObjName(yymsp[-3].minor.yy0->value), true);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 294: /* exprx ::= expr AND expr */
- case 295: /* exprx ::= expr OR expr */ yytestcase(yyruleno==295);
- case 296: /* exprx ::= expr LT|GT|GE|LE expr */ yytestcase(yyruleno==296);
- case 297: /* exprx ::= expr EQ|NE expr */ yytestcase(yyruleno==297);
- case 298: /* exprx ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr */ yytestcase(yyruleno==298);
- case 299: /* exprx ::= expr PLUS|MINUS expr */ yytestcase(yyruleno==299);
- case 300: /* exprx ::= expr STAR|SLASH|REM expr */ yytestcase(yyruleno==300);
- case 301: /* exprx ::= expr CONCAT expr */ yytestcase(yyruleno==301);
+ case 295: /* exprx ::= expr AND expr */
+ case 296: /* exprx ::= expr OR expr */ yytestcase(yyruleno==296);
+ case 297: /* exprx ::= expr LT|GT|GE|LE expr */ yytestcase(yyruleno==297);
+ case 298: /* exprx ::= expr EQ|NE expr */ yytestcase(yyruleno==298);
+ case 299: /* exprx ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr */ yytestcase(yyruleno==299);
+ case 300: /* exprx ::= expr PLUS|MINUS expr */ yytestcase(yyruleno==300);
+ case 301: /* exprx ::= expr STAR|SLASH|REM expr */ yytestcase(yyruleno==301);
+ case 302: /* exprx ::= expr CONCAT expr */ yytestcase(yyruleno==302);
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initBinOp(yymsp[-2].minor.yy186, yymsp[-1].minor.yy0->value, yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initBinOp(yymsp[-2].minor.yy176, yymsp[-1].minor.yy0->value, yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 302: /* exprx ::= expr not_opt likeop expr */
+ case 303: /* exprx ::= expr not_opt likeop expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initLike(yymsp[-3].minor.yy186, *(yymsp[-2].minor.yy225), *(yymsp[-1].minor.yy274), yymsp[0].minor.yy186);
- delete yymsp[-2].minor.yy225;
- delete yymsp[-1].minor.yy274;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initLike(yymsp[-3].minor.yy176, *(yymsp[-2].minor.yy35), *(yymsp[-1].minor.yy104), yymsp[0].minor.yy176);
+ delete yymsp[-2].minor.yy35;
+ delete yymsp[-1].minor.yy104;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 303: /* exprx ::= expr not_opt likeop expr ESCAPE expr */
+ case 304: /* exprx ::= expr not_opt likeop expr ESCAPE expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initLike(yymsp[-5].minor.yy186, *(yymsp[-4].minor.yy225), *(yymsp[-3].minor.yy274), yymsp[-2].minor.yy186, yymsp[0].minor.yy186);
- delete yymsp[-4].minor.yy225;
- delete yymsp[-3].minor.yy274;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initLike(yymsp[-5].minor.yy176, *(yymsp[-4].minor.yy35), *(yymsp[-3].minor.yy104), yymsp[-2].minor.yy176, yymsp[0].minor.yy176);
+ delete yymsp[-4].minor.yy35;
+ delete yymsp[-3].minor.yy104;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 304: /* exprx ::= expr ISNULL|NOTNULL */
+ case 305: /* exprx ::= expr ISNULL|NOTNULL */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initNull(yymsp[-1].minor.yy186, yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initNull(yymsp[-1].minor.yy176, yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 305: /* exprx ::= expr NOT NULL */
+ case 306: /* exprx ::= expr NOT NULL */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initNull(yymsp[-2].minor.yy186, "NOT NULL");
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initNull(yymsp[-2].minor.yy176, "NOT NULL");
+ objectForTokens = yygotominor.yy176;
}
break;
- case 306: /* exprx ::= expr IS not_opt expr */
+ case 307: /* exprx ::= expr IS not_opt expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initIs(yymsp[-3].minor.yy186, *(yymsp[-1].minor.yy225), yymsp[0].minor.yy186);
- delete yymsp[-1].minor.yy225;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initIs(yymsp[-3].minor.yy176, *(yymsp[-1].minor.yy35), yymsp[0].minor.yy176);
+ delete yymsp[-1].minor.yy35;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 307: /* exprx ::= expr IS NOT DISTINCT FROM expr */
+ case 308: /* exprx ::= expr IS NOT DISTINCT FROM expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initDistinct(yymsp[-5].minor.yy186, true, yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initDistinct(yymsp[-5].minor.yy176, true, yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 308: /* exprx ::= expr IS DISTINCT FROM expr */
+ case 309: /* exprx ::= expr IS DISTINCT FROM expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initDistinct(yymsp[-4].minor.yy186, false, yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initDistinct(yymsp[-4].minor.yy176, false, yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 309: /* exprx ::= NOT expr */
+ case 310: /* exprx ::= NOT expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initUnaryOp(yymsp[0].minor.yy186, yymsp[-1].minor.yy0->value);
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initUnaryOp(yymsp[0].minor.yy176, yymsp[-1].minor.yy0->value);
}
break;
- case 310: /* exprx ::= BITNOT expr */
- case 312: /* exprx ::= PLUS expr */ yytestcase(yyruleno==312);
+ case 311: /* exprx ::= BITNOT expr */
+ case 313: /* exprx ::= PLUS expr */ yytestcase(yyruleno==313);
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initUnaryOp(yymsp[0].minor.yy186, yymsp[-1].minor.yy0->value);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initUnaryOp(yymsp[0].minor.yy176, yymsp[-1].minor.yy0->value);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 311: /* exprx ::= MINUS expr */
+ case 312: /* exprx ::= MINUS expr */
{
- yygotominor.yy186 = new SqliteExpr();
- if (yymsp[0].minor.yy186->mode == SqliteExpr::Mode::LITERAL_VALUE &&
+ yygotominor.yy176 = new SqliteExpr();
+ if (yymsp[0].minor.yy176->mode == SqliteExpr::Mode::LITERAL_VALUE &&
parserContext->isCandidateForMaxNegativeNumber() &&
- yymsp[0].minor.yy186->literalValue == static_cast<qint64>(0L))
+ yymsp[0].minor.yy176->literalValue == static_cast<qint64>(0L))
{
- yygotominor.yy186->initLiteral(std::numeric_limits<qint64>::min());
- delete yymsp[0].minor.yy186;
+ yygotominor.yy176->initLiteral(std::numeric_limits<qint64>::min());
+ delete yymsp[0].minor.yy176;
}
else
{
- yygotominor.yy186->initUnaryOp(yymsp[0].minor.yy186, yymsp[-1].minor.yy0->value);
+ yygotominor.yy176->initUnaryOp(yymsp[0].minor.yy176, yymsp[-1].minor.yy0->value);
}
- objectForTokens = yygotominor.yy186;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 313: /* exprx ::= expr PTR expr */
+ case 314: /* exprx ::= expr PTR expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initPtrOp(yymsp[-2].minor.yy186, yymsp[-1].minor.yy0->value, yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initPtrOp(yymsp[-2].minor.yy176, yymsp[-1].minor.yy0->value, yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 314: /* exprx ::= expr not_opt BETWEEN expr AND expr */
+ case 315: /* exprx ::= expr not_opt BETWEEN expr AND expr */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initBetween(yymsp[-5].minor.yy186, *(yymsp[-4].minor.yy225), yymsp[-2].minor.yy186, yymsp[0].minor.yy186);
- delete yymsp[-4].minor.yy225;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initBetween(yymsp[-5].minor.yy176, *(yymsp[-4].minor.yy35), yymsp[-2].minor.yy176, yymsp[0].minor.yy176);
+ delete yymsp[-4].minor.yy35;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 315: /* exprx ::= expr not_opt IN LP exprlist RP */
+ case 316: /* exprx ::= expr not_opt IN LP exprlist RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initIn(yymsp[-5].minor.yy186, *(yymsp[-4].minor.yy225), *(yymsp[-1].minor.yy615));
- delete yymsp[-4].minor.yy225;
- delete yymsp[-1].minor.yy615;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initIn(yymsp[-5].minor.yy176, *(yymsp[-4].minor.yy35), *(yymsp[-1].minor.yy567));
+ delete yymsp[-4].minor.yy35;
+ delete yymsp[-1].minor.yy567;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 316: /* exprx ::= LP select RP */
+ case 317: /* exprx ::= LP select RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initSubSelect(yymsp[-1].minor.yy297);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initSubSelect(yymsp[-1].minor.yy73);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 317: /* exprx ::= expr not_opt IN LP select RP */
+ case 318: /* exprx ::= expr not_opt IN LP select RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initIn(yymsp[-5].minor.yy186, *(yymsp[-4].minor.yy225), yymsp[-1].minor.yy297);
- delete yymsp[-4].minor.yy225;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initIn(yymsp[-5].minor.yy176, *(yymsp[-4].minor.yy35), yymsp[-1].minor.yy73);
+ delete yymsp[-4].minor.yy35;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 318: /* exprx ::= expr not_opt IN nm dbnm */
+ case 319: /* exprx ::= expr not_opt IN nm dbnm */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initIn(yymsp[-4].minor.yy186, *(yymsp[-3].minor.yy225), *(yymsp[-1].minor.yy319), *(yymsp[0].minor.yy319));
- delete yymsp[-3].minor.yy225;
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initIn(yymsp[-4].minor.yy176, *(yymsp[-3].minor.yy35), *(yymsp[-1].minor.yy255), *(yymsp[0].minor.yy255));
+ delete yymsp[-3].minor.yy35;
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 319: /* exprx ::= EXISTS LP select RP */
+ case 320: /* exprx ::= EXISTS LP select RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initExists(yymsp[-1].minor.yy297);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initExists(yymsp[-1].minor.yy73);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 320: /* exprx ::= CASE case_operand case_exprlist case_else END */
+ case 321: /* exprx ::= CASE case_operand case_exprlist case_else END */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initCase(yymsp[-3].minor.yy186, *(yymsp[-2].minor.yy615), yymsp[-1].minor.yy186);
- delete yymsp[-2].minor.yy615;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initCase(yymsp[-3].minor.yy176, *(yymsp[-2].minor.yy567), yymsp[-1].minor.yy176);
+ delete yymsp[-2].minor.yy567;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 321: /* exprx ::= RAISE LP IGNORE RP */
+ case 322: /* exprx ::= RAISE LP IGNORE RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initRaise(yymsp[-1].minor.yy0->value);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initRaise(yymsp[-1].minor.yy0->value);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 322: /* exprx ::= RAISE LP raisetype COMMA nm RP */
+ case 323: /* exprx ::= RAISE LP raisetype COMMA nm RP */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initRaise(yymsp[-3].minor.yy0->value, *(yymsp[-1].minor.yy319));
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initRaise(yymsp[-3].minor.yy0->value, *(yymsp[-1].minor.yy255));
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 323: /* exprx ::= ID LP distinct exprlist RP filter_over */
+ case 324: /* exprx ::= ID LP distinct exprlist RP filter_over */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initWindowFunction(stripObjName(yymsp[-5].minor.yy0->value), *(yymsp[-3].minor.yy130), *(yymsp[-2].minor.yy615), yymsp[0].minor.yy181);
- delete yymsp[-3].minor.yy130;
- delete yymsp[-2].minor.yy615;
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initWindowFunction(stripObjName(yymsp[-5].minor.yy0->value), *(yymsp[-3].minor.yy562), *(yymsp[-2].minor.yy567), yymsp[0].minor.yy487);
+ delete yymsp[-3].minor.yy562;
+ delete yymsp[-2].minor.yy567;
+ objectForTokens = yygotominor.yy176;
}
break;
- case 324: /* exprx ::= ID LP STAR RP filter_over */
+ case 325: /* exprx ::= ID LP STAR RP filter_over */
{
- yygotominor.yy186 = new SqliteExpr();
- yygotominor.yy186->initWindowFunction(stripObjName(yymsp[-4].minor.yy0->value), yymsp[0].minor.yy181);
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ yygotominor.yy176->initWindowFunction(stripObjName(yymsp[-4].minor.yy0->value), yymsp[0].minor.yy487);
+ objectForTokens = yygotominor.yy176;
}
break;
- case 325: /* expr ::= */
+ case 326: /* expr ::= */
{
- yygotominor.yy186 = new SqliteExpr();
- objectForTokens = yygotominor.yy186;
+ yygotominor.yy176 = new SqliteExpr();
+ objectForTokens = yygotominor.yy176;
parserContext->minorErrorAfterLastToken("Syntax error <expr>");
}
break;
- case 329: /* likeop ::= LIKE_KW|MATCH */
-{yygotominor.yy274 = new SqliteExpr::LikeOp(SqliteExpr::likeOp(yymsp[0].minor.yy0->value));}
+ case 332: /* likeop ::= LIKE_KW|MATCH */
+{yygotominor.yy104 = new SqliteExpr::LikeOp(SqliteExpr::likeOp(yymsp[0].minor.yy0->value));}
break;
- case 330: /* case_exprlist ::= case_exprlist WHEN expr THEN expr */
+ case 333: /* case_exprlist ::= case_exprlist WHEN expr THEN expr */
{
- yymsp[-4].minor.yy615->append(yymsp[-2].minor.yy186);
- yymsp[-4].minor.yy615->append(yymsp[0].minor.yy186);
- yygotominor.yy615 = yymsp[-4].minor.yy615;
+ yymsp[-4].minor.yy567->append(yymsp[-2].minor.yy176);
+ yymsp[-4].minor.yy567->append(yymsp[0].minor.yy176);
+ yygotominor.yy567 = yymsp[-4].minor.yy567;
}
break;
- case 331: /* case_exprlist ::= WHEN expr THEN expr */
+ case 334: /* case_exprlist ::= WHEN expr THEN expr */
{
- yygotominor.yy615 = new ParserExprList();
- yygotominor.yy615->append(yymsp[-2].minor.yy186);
- yygotominor.yy615->append(yymsp[0].minor.yy186);
+ yygotominor.yy567 = new ParserExprList();
+ yygotominor.yy567->append(yymsp[-2].minor.yy176);
+ yygotominor.yy567->append(yymsp[0].minor.yy176);
}
break;
- case 338: /* nexprlist ::= nexprlist COMMA expr */
+ case 341: /* nexprlist ::= nexprlist COMMA expr */
{
- yymsp[-2].minor.yy615->append(yymsp[0].minor.yy186);
- yygotominor.yy615 = yymsp[-2].minor.yy615;
+ yymsp[-2].minor.yy567->append(yymsp[0].minor.yy176);
+ yygotominor.yy567 = yymsp[-2].minor.yy567;
DONT_INHERIT_TOKENS("nexprlist");
}
break;
- case 339: /* nexprlist ::= exprx */
+ case 342: /* nexprlist ::= exprx */
{
- yygotominor.yy615 = new ParserExprList();
- yygotominor.yy615->append(yymsp[0].minor.yy186);
+ yygotominor.yy567 = new ParserExprList();
+ yygotominor.yy567->append(yymsp[0].minor.yy176);
}
break;
- case 340: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt */
+ case 343: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt */
{
- yygotominor.yy41 = new SqliteCreateIndex(
- *(yymsp[-10].minor.yy225),
- *(yymsp[-8].minor.yy225),
- *(yymsp[-7].minor.yy319),
- *(yymsp[-6].minor.yy319),
- *(yymsp[-4].minor.yy319),
- *(yymsp[-2].minor.yy226),
- yymsp[0].minor.yy186
+ yygotominor.yy635 = new SqliteCreateIndex(
+ *(yymsp[-10].minor.yy35),
+ *(yymsp[-8].minor.yy35),
+ *(yymsp[-7].minor.yy255),
+ *(yymsp[-6].minor.yy255),
+ *(yymsp[-4].minor.yy255),
+ *(yymsp[-2].minor.yy499),
+ yymsp[0].minor.yy176
);
- delete yymsp[-8].minor.yy225;
- delete yymsp[-10].minor.yy225;
- delete yymsp[-7].minor.yy319;
- delete yymsp[-6].minor.yy319;
- delete yymsp[-4].minor.yy319;
- delete yymsp[-2].minor.yy226;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-8].minor.yy35;
+ delete yymsp[-10].minor.yy35;
+ delete yymsp[-7].minor.yy255;
+ delete yymsp[-6].minor.yy255;
+ delete yymsp[-4].minor.yy255;
+ delete yymsp[-2].minor.yy499;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 341: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON ID_TAB */
+ case 344: /* cmd ::= CREATE uniqueflag INDEX ifnotexists nm dbnm ON ID_TAB */
{ yy_destructor(yypParser,203,&yymsp[-3].minor);
}
break;
- case 346: /* idxlist_opt ::= */
-{yygotominor.yy627 = new ParserIndexedColumnList();}
+ case 349: /* idxlist_opt ::= */
+{yygotominor.yy527 = new ParserIndexedColumnList();}
break;
- case 347: /* idxlist_opt ::= LP idxlist RP */
-{yygotominor.yy627 = yymsp[-1].minor.yy627;}
+ case 350: /* idxlist_opt ::= LP idxlist RP */
+{yygotominor.yy527 = yymsp[-1].minor.yy527;}
break;
- case 348: /* idxlist ::= idxlist COMMA idxlist_single */
+ case 351: /* idxlist ::= idxlist COMMA idxlist_single */
{
- yymsp[-2].minor.yy627->append(yymsp[0].minor.yy110);
- yygotominor.yy627 = yymsp[-2].minor.yy627;
+ yymsp[-2].minor.yy527->append(yymsp[0].minor.yy540);
+ yygotominor.yy527 = yymsp[-2].minor.yy527;
DONT_INHERIT_TOKENS("idxlist");
}
break;
- case 349: /* idxlist ::= idxlist_single */
+ case 352: /* idxlist ::= idxlist_single */
{
- yygotominor.yy627 = new ParserIndexedColumnList();
- yygotominor.yy627->append(yymsp[0].minor.yy110);
+ yygotominor.yy527 = new ParserIndexedColumnList();
+ yygotominor.yy527->append(yymsp[0].minor.yy540);
}
break;
- case 350: /* idxlist_single ::= nm collate sortorder */
- case 351: /* idxlist_single ::= ID_COL */ yytestcase(yyruleno==351);
+ case 353: /* idxlist_single ::= nm collate sortorder */
+ case 354: /* idxlist_single ::= ID_COL */ yytestcase(yyruleno==354);
{
SqliteIndexedColumn* obj =
new SqliteIndexedColumn(
- *(yymsp[-2].minor.yy319),
- *(yymsp[-1].minor.yy319),
- *(yymsp[0].minor.yy35)
+ *(yymsp[-2].minor.yy255),
+ *(yymsp[-1].minor.yy255),
+ *(yymsp[0].minor.yy645)
);
- yygotominor.yy110 = obj;
- delete yymsp[0].minor.yy35;
- delete yymsp[-2].minor.yy319;
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy110;
+ yygotominor.yy540 = obj;
+ delete yymsp[0].minor.yy645;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy540;
}
break;
- case 355: /* cmd ::= DROP INDEX ifexists fullname */
+ case 358: /* cmd ::= DROP INDEX ifexists fullname */
{
- yygotominor.yy41 = new SqliteDropIndex(*(yymsp[-1].minor.yy225), yymsp[0].minor.yy396->name1, yymsp[0].minor.yy396->name2);
- delete yymsp[-1].minor.yy225;
- delete yymsp[0].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteDropIndex(*(yymsp[-1].minor.yy35), yymsp[0].minor.yy520->name1, yymsp[0].minor.yy520->name2);
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[0].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 358: /* cmd ::= VACUUM vinto */
+ case 361: /* cmd ::= VACUUM vinto */
{
- yygotominor.yy41 = new SqliteVacuum(yymsp[0].minor.yy186);
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteVacuum(yymsp[0].minor.yy176);
+ objectForTokens = yygotominor.yy635;
}
break;
- case 359: /* cmd ::= VACUUM nm vinto */
+ case 362: /* cmd ::= VACUUM nm vinto */
{
- yygotominor.yy41 = new SqliteVacuum(*(yymsp[-1].minor.yy319), yymsp[0].minor.yy186);
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteVacuum(*(yymsp[-1].minor.yy255), yymsp[0].minor.yy176);
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 362: /* cmd ::= PRAGMA nm dbnm */
+ case 365: /* cmd ::= PRAGMA nm dbnm */
{
- yygotominor.yy41 = new SqlitePragma(*(yymsp[-1].minor.yy319), *(yymsp[0].minor.yy319));
- delete yymsp[-1].minor.yy319;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqlitePragma(*(yymsp[-1].minor.yy255), *(yymsp[0].minor.yy255));
+ delete yymsp[-1].minor.yy255;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 363: /* cmd ::= PRAGMA nm dbnm EQ nmnum */
- case 365: /* cmd ::= PRAGMA nm dbnm EQ minus_num */ yytestcase(yyruleno==365);
+ case 366: /* cmd ::= PRAGMA nm dbnm EQ nmnum */
+ case 368: /* cmd ::= PRAGMA nm dbnm EQ minus_num */ yytestcase(yyruleno==368);
{
- yygotominor.yy41 = new SqlitePragma(*(yymsp[-3].minor.yy319), *(yymsp[-2].minor.yy319), *(yymsp[0].minor.yy393), true);
- delete yymsp[-3].minor.yy319;
- delete yymsp[-2].minor.yy319;
- delete yymsp[0].minor.yy393;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqlitePragma(*(yymsp[-3].minor.yy255), *(yymsp[-2].minor.yy255), *(yymsp[0].minor.yy629), true);
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[0].minor.yy629;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 364: /* cmd ::= PRAGMA nm dbnm LP nmnum RP */
- case 366: /* cmd ::= PRAGMA nm dbnm LP minus_num RP */ yytestcase(yyruleno==366);
+ case 367: /* cmd ::= PRAGMA nm dbnm LP nmnum RP */
+ case 369: /* cmd ::= PRAGMA nm dbnm LP minus_num RP */ yytestcase(yyruleno==369);
{
- yygotominor.yy41 = new SqlitePragma(*(yymsp[-4].minor.yy319), *(yymsp[-3].minor.yy319), *(yymsp[-1].minor.yy393), false);
- delete yymsp[-4].minor.yy319;
- delete yymsp[-3].minor.yy319;
- delete yymsp[-1].minor.yy393;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqlitePragma(*(yymsp[-4].minor.yy255), *(yymsp[-3].minor.yy255), *(yymsp[-1].minor.yy629), false);
+ delete yymsp[-4].minor.yy255;
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-1].minor.yy629;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 370: /* nmnum ::= nm */
+ case 373: /* nmnum ::= nm */
{
- yygotominor.yy393 = new QVariant(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
+ yygotominor.yy629 = new QVariant(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
}
break;
- case 371: /* nmnum ::= ON */
- case 372: /* nmnum ::= DELETE */ yytestcase(yyruleno==372);
- case 373: /* nmnum ::= DEFAULT */ yytestcase(yyruleno==373);
-{yygotominor.yy393 = new QVariant(yymsp[0].minor.yy0->value);}
+ case 374: /* nmnum ::= ON */
+ case 375: /* nmnum ::= DELETE */ yytestcase(yyruleno==375);
+ case 376: /* nmnum ::= DEFAULT */ yytestcase(yyruleno==376);
+{yygotominor.yy629 = new QVariant(yymsp[0].minor.yy0->value);}
break;
- case 376: /* minus_num ::= MINUS number */
+ case 379: /* minus_num ::= MINUS number */
{
- if (yymsp[0].minor.yy393->type() == QVariant::Double)
- *(yymsp[0].minor.yy393) = -(yymsp[0].minor.yy393->toDouble());
- else if (yymsp[0].minor.yy393->type() == QVariant::LongLong)
+ if (yymsp[0].minor.yy629->type() == QVariant::Double)
+ *(yymsp[0].minor.yy629) = -(yymsp[0].minor.yy629->toDouble());
+ else if (yymsp[0].minor.yy629->type() == QVariant::LongLong)
{
if (parserContext->isCandidateForMaxNegativeNumber())
- *(yymsp[0].minor.yy393) = std::numeric_limits<qint64>::min();
+ *(yymsp[0].minor.yy629) = std::numeric_limits<qint64>::min();
else
- *(yymsp[0].minor.yy393) = -(yymsp[0].minor.yy393->toLongLong());
+ *(yymsp[0].minor.yy629) = -(yymsp[0].minor.yy629->toLongLong());
}
else
Q_ASSERT_X(true, "producing minus number", "QVariant is neither of Double or LongLong.");
- yygotominor.yy393 = yymsp[0].minor.yy393;
- }
- break;
- case 379: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list END */
-{
- yygotominor.yy41 = new SqliteCreateTrigger(
- *(yymsp[-13].minor.yy130),
- *(yymsp[-11].minor.yy225),
- *(yymsp[-10].minor.yy319),
- *(yymsp[-9].minor.yy319),
- *(yymsp[-5].minor.yy319),
- *(yymsp[-8].minor.yy120),
- yymsp[-7].minor.yy259,
- *(yymsp[-4].minor.yy456),
- yymsp[-3].minor.yy186,
- *(yymsp[-1].minor.yy240),
+ yygotominor.yy629 = yymsp[0].minor.yy629;
+ }
+ break;
+ case 382: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list END */
+{
+ yygotominor.yy635 = new SqliteCreateTrigger(
+ *(yymsp[-13].minor.yy562),
+ *(yymsp[-11].minor.yy35),
+ *(yymsp[-10].minor.yy255),
+ *(yymsp[-9].minor.yy255),
+ *(yymsp[-5].minor.yy255),
+ *(yymsp[-8].minor.yy612),
+ yymsp[-7].minor.yy407,
+ *(yymsp[-4].minor.yy403),
+ yymsp[-3].minor.yy176,
+ *(yymsp[-1].minor.yy575),
3
);
- delete yymsp[-11].minor.yy225;
- delete yymsp[-13].minor.yy130;
- delete yymsp[-8].minor.yy120;
- delete yymsp[-4].minor.yy456;
- delete yymsp[-10].minor.yy319;
- delete yymsp[-5].minor.yy319;
- delete yymsp[-9].minor.yy319;
- delete yymsp[-1].minor.yy240;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-11].minor.yy35;
+ delete yymsp[-13].minor.yy562;
+ delete yymsp[-8].minor.yy612;
+ delete yymsp[-4].minor.yy403;
+ delete yymsp[-10].minor.yy255;
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-9].minor.yy255;
+ delete yymsp[-1].minor.yy575;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 380: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause */
+ case 383: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause */
{
QList<SqliteQuery *> CL;
- yygotominor.yy41 = new SqliteCreateTrigger(
- *(yymsp[-10].minor.yy130),
- *(yymsp[-8].minor.yy225),
- *(yymsp[-7].minor.yy319),
- *(yymsp[-6].minor.yy319),
- *(yymsp[-2].minor.yy319),
- *(yymsp[-5].minor.yy120),
- yymsp[-4].minor.yy259,
- *(yymsp[-1].minor.yy456),
- yymsp[0].minor.yy186,
+ yygotominor.yy635 = new SqliteCreateTrigger(
+ *(yymsp[-10].minor.yy562),
+ *(yymsp[-8].minor.yy35),
+ *(yymsp[-7].minor.yy255),
+ *(yymsp[-6].minor.yy255),
+ *(yymsp[-2].minor.yy255),
+ *(yymsp[-5].minor.yy612),
+ yymsp[-4].minor.yy407,
+ *(yymsp[-1].minor.yy403),
+ yymsp[0].minor.yy176,
CL,
3
);
- delete yymsp[-8].minor.yy225;
- delete yymsp[-10].minor.yy130;
- delete yymsp[-5].minor.yy120;
- delete yymsp[-1].minor.yy456;
- delete yymsp[-7].minor.yy319;
- delete yymsp[-2].minor.yy319;
- delete yymsp[-6].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-8].minor.yy35;
+ delete yymsp[-10].minor.yy562;
+ delete yymsp[-5].minor.yy612;
+ delete yymsp[-1].minor.yy403;
+ delete yymsp[-7].minor.yy255;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[-6].minor.yy255;
+ objectForTokens = yygotominor.yy635;
parserContext->minorErrorAfterLastToken("Syntax error");
}
break;
- case 381: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list */
+ case 384: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON nm foreach_clause when_clause BEGIN trigger_cmd_list */
{
- yygotominor.yy41 = new SqliteCreateTrigger(
- *(yymsp[-12].minor.yy130),
- *(yymsp[-10].minor.yy225),
- *(yymsp[-9].minor.yy319),
- *(yymsp[-8].minor.yy319),
- *(yymsp[-4].minor.yy319),
- *(yymsp[-7].minor.yy120),
- yymsp[-6].minor.yy259,
- *(yymsp[-3].minor.yy456),
- yymsp[-2].minor.yy186,
- *(yymsp[0].minor.yy240),
+ yygotominor.yy635 = new SqliteCreateTrigger(
+ *(yymsp[-12].minor.yy562),
+ *(yymsp[-10].minor.yy35),
+ *(yymsp[-9].minor.yy255),
+ *(yymsp[-8].minor.yy255),
+ *(yymsp[-4].minor.yy255),
+ *(yymsp[-7].minor.yy612),
+ yymsp[-6].minor.yy407,
+ *(yymsp[-3].minor.yy403),
+ yymsp[-2].minor.yy176,
+ *(yymsp[0].minor.yy575),
3
);
- delete yymsp[-10].minor.yy225;
- delete yymsp[-12].minor.yy130;
- delete yymsp[-7].minor.yy120;
- delete yymsp[-3].minor.yy456;
- delete yymsp[-9].minor.yy319;
- delete yymsp[-4].minor.yy319;
- delete yymsp[-8].minor.yy319;
- delete yymsp[0].minor.yy240;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-10].minor.yy35;
+ delete yymsp[-12].minor.yy562;
+ delete yymsp[-7].minor.yy612;
+ delete yymsp[-3].minor.yy403;
+ delete yymsp[-9].minor.yy255;
+ delete yymsp[-4].minor.yy255;
+ delete yymsp[-8].minor.yy255;
+ delete yymsp[0].minor.yy575;
+ objectForTokens = yygotominor.yy635;
parserContext->minorErrorAfterLastToken("Syntax error");
}
break;
- case 382: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON ID_TAB */
+ case 385: /* cmd ::= CREATE temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON ID_TAB */
{ yy_destructor(yypParser,205,&yymsp[-8].minor);
yy_destructor(yypParser,203,&yymsp[-5].minor);
- yy_destructor(yypParser,298,&yymsp[-3].minor);
- yy_destructor(yypParser,299,&yymsp[-2].minor);
+ yy_destructor(yypParser,299,&yymsp[-3].minor);
+ yy_destructor(yypParser,300,&yymsp[-2].minor);
}
break;
- case 385: /* trigger_time ::= BEFORE */
-{yygotominor.yy120 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::BEFORE);}
+ case 388: /* trigger_time ::= BEFORE */
+{yygotominor.yy612 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::BEFORE);}
break;
- case 386: /* trigger_time ::= AFTER */
-{yygotominor.yy120 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::AFTER);}
+ case 389: /* trigger_time ::= AFTER */
+{yygotominor.yy612 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::AFTER);}
break;
- case 387: /* trigger_time ::= INSTEAD OF */
-{yygotominor.yy120 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::INSTEAD_OF);}
+ case 390: /* trigger_time ::= INSTEAD OF */
+{yygotominor.yy612 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::INSTEAD_OF);}
break;
- case 388: /* trigger_time ::= */
-{yygotominor.yy120 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::null);}
+ case 391: /* trigger_time ::= */
+{yygotominor.yy612 = new SqliteCreateTrigger::Time(SqliteCreateTrigger::Time::null);}
break;
- case 389: /* trigger_event ::= DELETE */
+ case 392: /* trigger_event ::= DELETE */
{
- yygotominor.yy259 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::DELETE);
- objectForTokens = yygotominor.yy259;
+ yygotominor.yy407 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::DELETE);
+ objectForTokens = yygotominor.yy407;
}
break;
- case 390: /* trigger_event ::= INSERT */
+ case 393: /* trigger_event ::= INSERT */
{
- yygotominor.yy259 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::INSERT);
- objectForTokens = yygotominor.yy259;
+ yygotominor.yy407 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::INSERT);
+ objectForTokens = yygotominor.yy407;
}
break;
- case 391: /* trigger_event ::= UPDATE */
+ case 394: /* trigger_event ::= UPDATE */
{
- yygotominor.yy259 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::UPDATE);
- objectForTokens = yygotominor.yy259;
+ yygotominor.yy407 = new SqliteCreateTrigger::Event(SqliteCreateTrigger::Event::UPDATE);
+ objectForTokens = yygotominor.yy407;
}
break;
- case 392: /* trigger_event ::= UPDATE OF idlist */
+ case 395: /* trigger_event ::= UPDATE OF idlist */
{
- yygotominor.yy259 = new SqliteCreateTrigger::Event(*(yymsp[0].minor.yy173));
- delete yymsp[0].minor.yy173;
- objectForTokens = yygotominor.yy259;
+ yygotominor.yy407 = new SqliteCreateTrigger::Event(*(yymsp[0].minor.yy336));
+ delete yymsp[0].minor.yy336;
+ objectForTokens = yygotominor.yy407;
}
break;
- case 393: /* foreach_clause ::= */
-{yygotominor.yy456 = new SqliteCreateTrigger::Scope(SqliteCreateTrigger::Scope::null);}
+ case 396: /* foreach_clause ::= */
+{yygotominor.yy403 = new SqliteCreateTrigger::Scope(SqliteCreateTrigger::Scope::null);}
break;
- case 394: /* foreach_clause ::= FOR EACH ROW */
-{yygotominor.yy456 = new SqliteCreateTrigger::Scope(SqliteCreateTrigger::Scope::FOR_EACH_ROW);}
+ case 397: /* foreach_clause ::= FOR EACH ROW */
+{yygotominor.yy403 = new SqliteCreateTrigger::Scope(SqliteCreateTrigger::Scope::FOR_EACH_ROW);}
break;
- case 397: /* trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI */
+ case 400: /* trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI */
{
- yymsp[-2].minor.yy240->append(yymsp[-1].minor.yy41);
- yygotominor.yy240 = yymsp[-2].minor.yy240;
+ yymsp[-2].minor.yy575->append(yymsp[-1].minor.yy635);
+ yygotominor.yy575 = yymsp[-2].minor.yy575;
DONT_INHERIT_TOKENS("trigger_cmd_list");
}
break;
- case 398: /* trigger_cmd_list ::= trigger_cmd SEMI */
+ case 401: /* trigger_cmd_list ::= trigger_cmd SEMI */
{
- yygotominor.yy240 = new ParserQueryList();
- yygotominor.yy240->append(yymsp[-1].minor.yy41);
+ yygotominor.yy575 = new ParserQueryList();
+ yygotominor.yy575->append(yymsp[-1].minor.yy635);
}
break;
- case 399: /* trigger_cmd_list ::= SEMI */
+ case 402: /* trigger_cmd_list ::= SEMI */
{
- yygotominor.yy240 = new ParserQueryList();
+ yygotominor.yy575 = new ParserQueryList();
parserContext->minorErrorAfterLastToken("Syntax error");
}
break;
- case 404: /* raisetype ::= ROLLBACK|ABORT|FAIL */
+ case 407: /* raisetype ::= ROLLBACK|ABORT|FAIL */
{yygotominor.yy0 = yymsp[0].minor.yy0;}
break;
- case 405: /* cmd ::= DROP TRIGGER ifexists fullname */
+ case 408: /* cmd ::= DROP TRIGGER ifexists fullname */
{
- yygotominor.yy41 = new SqliteDropTrigger(*(yymsp[-1].minor.yy225), yymsp[0].minor.yy396->name1, yymsp[0].minor.yy396->name2);
- delete yymsp[-1].minor.yy225;
- delete yymsp[0].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteDropTrigger(*(yymsp[-1].minor.yy35), yymsp[0].minor.yy520->name1, yymsp[0].minor.yy520->name2);
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[0].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 408: /* cmd ::= ATTACH database_kw_opt expr AS expr key_opt */
+ case 411: /* cmd ::= ATTACH database_kw_opt expr AS expr key_opt */
{
- yygotominor.yy41 = new SqliteAttach(*(yymsp[-4].minor.yy225), yymsp[-3].minor.yy186, yymsp[-1].minor.yy186, yymsp[0].minor.yy186);
- delete yymsp[-4].minor.yy225;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteAttach(*(yymsp[-4].minor.yy35), yymsp[-3].minor.yy176, yymsp[-1].minor.yy176, yymsp[0].minor.yy176);
+ delete yymsp[-4].minor.yy35;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 409: /* cmd ::= DETACH database_kw_opt expr */
+ case 412: /* cmd ::= DETACH database_kw_opt expr */
{
- yygotominor.yy41 = new SqliteDetach(*(yymsp[-1].minor.yy225), yymsp[0].minor.yy186);
- delete yymsp[-1].minor.yy225;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteDetach(*(yymsp[-1].minor.yy35), yymsp[0].minor.yy176);
+ delete yymsp[-1].minor.yy35;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 414: /* cmd ::= REINDEX */
-{yygotominor.yy41 = new SqliteReindex();}
+ case 417: /* cmd ::= REINDEX */
+{yygotominor.yy635 = new SqliteReindex();}
break;
- case 415: /* cmd ::= REINDEX nm dbnm */
- case 416: /* cmd ::= REINDEX ID_COLLATE */ yytestcase(yyruleno==416);
+ case 418: /* cmd ::= REINDEX nm dbnm */
+ case 419: /* cmd ::= REINDEX ID_COLLATE */ yytestcase(yyruleno==419);
{
- yygotominor.yy41 = new SqliteReindex(*(yymsp[-1].minor.yy319), *(yymsp[0].minor.yy319));
- delete yymsp[-1].minor.yy319;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteReindex(*(yymsp[-1].minor.yy255), *(yymsp[0].minor.yy255));
+ delete yymsp[-1].minor.yy255;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 419: /* cmd ::= ANALYZE */
+ case 422: /* cmd ::= ANALYZE */
{
- yygotominor.yy41 = new SqliteAnalyze();
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteAnalyze();
+ objectForTokens = yygotominor.yy635;
}
break;
- case 420: /* cmd ::= ANALYZE nm dbnm */
+ case 423: /* cmd ::= ANALYZE nm dbnm */
{
- yygotominor.yy41 = new SqliteAnalyze(*(yymsp[-1].minor.yy319), *(yymsp[0].minor.yy319));
- delete yymsp[-1].minor.yy319;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ yygotominor.yy635 = new SqliteAnalyze(*(yymsp[-1].minor.yy255), *(yymsp[0].minor.yy255));
+ delete yymsp[-1].minor.yy255;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 423: /* cmd ::= ALTER TABLE fullname RENAME TO nm */
+ case 426: /* cmd ::= ALTER TABLE fullname RENAME TO nm */
{
- yygotominor.yy41 = new SqliteAlterTable(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
- *(yymsp[0].minor.yy319)
+ yygotominor.yy635 = new SqliteAlterTable(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ *(yymsp[0].minor.yy255)
);
- delete yymsp[0].minor.yy319;
- delete yymsp[-3].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[0].minor.yy255;
+ delete yymsp[-3].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 424: /* cmd ::= ALTER TABLE fullname ADD kwcolumn_opt column */
+ case 427: /* cmd ::= ALTER TABLE fullname ADD kwcolumn_opt column */
{
- yygotominor.yy41 = new SqliteAlterTable(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
- *(yymsp[-1].minor.yy225),
- yymsp[0].minor.yy3
+ yygotominor.yy635 = new SqliteAlterTable(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ *(yymsp[-1].minor.yy35),
+ yymsp[0].minor.yy115
);
- delete yymsp[-1].minor.yy225;
- delete yymsp[-3].minor.yy396;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[-3].minor.yy520;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 425: /* cmd ::= ALTER TABLE fullname DROP kwcolumn_opt nm */
+ case 428: /* cmd ::= ALTER TABLE fullname DROP kwcolumn_opt nm */
{
- yygotominor.yy41 = new SqliteAlterTable(
- yymsp[-3].minor.yy396->name1,
- yymsp[-3].minor.yy396->name2,
- *(yymsp[-1].minor.yy225),
- *(yymsp[0].minor.yy319)
+ yygotominor.yy635 = new SqliteAlterTable(
+ yymsp[-3].minor.yy520->name1,
+ yymsp[-3].minor.yy520->name2,
+ *(yymsp[-1].minor.yy35),
+ *(yymsp[0].minor.yy255)
);
- delete yymsp[-1].minor.yy225;
- delete yymsp[-3].minor.yy396;
- delete yymsp[0].minor.yy319;
+ delete yymsp[-1].minor.yy35;
+ delete yymsp[-3].minor.yy520;
+ delete yymsp[0].minor.yy255;
}
break;
- case 426: /* cmd ::= ALTER TABLE fullname RENAME TO ID_TAB_NEW */
+ case 429: /* cmd ::= ALTER TABLE fullname RENAME TO ID_TAB_NEW */
{ yy_destructor(yypParser,207,&yymsp[-3].minor);
}
break;
- case 432: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm */
+ case 435: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm */
{
- yygotominor.yy41 = new SqliteCreateVirtualTable(
- *(yymsp[-4].minor.yy225),
- *(yymsp[-3].minor.yy319),
- *(yymsp[-2].minor.yy319),
- *(yymsp[0].minor.yy319)
+ yygotominor.yy635 = new SqliteCreateVirtualTable(
+ *(yymsp[-4].minor.yy35),
+ *(yymsp[-3].minor.yy255),
+ *(yymsp[-2].minor.yy255),
+ *(yymsp[0].minor.yy255)
);
- delete yymsp[-4].minor.yy225;
- delete yymsp[-3].minor.yy319;
- delete yymsp[-2].minor.yy319;
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-4].minor.yy35;
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-2].minor.yy255;
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 433: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm LP vtabarglist RP */
+ case 436: /* create_vtab ::= CREATE VIRTUAL TABLE ifnotexists nm dbnm USING nm LP vtabarglist RP */
{
- yygotominor.yy41 = new SqliteCreateVirtualTable(
- *(yymsp[-7].minor.yy225),
- *(yymsp[-6].minor.yy319),
- *(yymsp[-5].minor.yy319),
- *(yymsp[-3].minor.yy319),
- *(yymsp[-1].minor.yy173)
+ yygotominor.yy635 = new SqliteCreateVirtualTable(
+ *(yymsp[-7].minor.yy35),
+ *(yymsp[-6].minor.yy255),
+ *(yymsp[-5].minor.yy255),
+ *(yymsp[-3].minor.yy255),
+ *(yymsp[-1].minor.yy336)
);
- delete yymsp[-6].minor.yy319;
- delete yymsp[-5].minor.yy319;
- delete yymsp[-3].minor.yy319;
- delete yymsp[-7].minor.yy225;
- delete yymsp[-1].minor.yy173;
- objectForTokens = yygotominor.yy41;
+ delete yymsp[-6].minor.yy255;
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-3].minor.yy255;
+ delete yymsp[-7].minor.yy35;
+ delete yymsp[-1].minor.yy336;
+ objectForTokens = yygotominor.yy635;
}
break;
- case 436: /* vtabarglist ::= vtabarg */
+ case 439: /* vtabarglist ::= vtabarg */
{
- yygotominor.yy173 = new QStringList();
- yygotominor.yy173->append((yymsp[0].minor.yy319)->mid(1)); // mid(1) to skip the first whitespace added in vtabarg
- delete yymsp[0].minor.yy319;
+ yygotominor.yy336 = new QStringList();
+ yygotominor.yy336->append((yymsp[0].minor.yy255)->mid(1)); // mid(1) to skip the first whitespace added in vtabarg
+ delete yymsp[0].minor.yy255;
}
break;
- case 437: /* vtabarglist ::= vtabarglist COMMA vtabarg */
+ case 440: /* vtabarglist ::= vtabarglist COMMA vtabarg */
{
- yymsp[-2].minor.yy173->append((yymsp[0].minor.yy319)->mid(1)); // mid(1) to skip the first whitespace added in vtabarg
- yygotominor.yy173 = yymsp[-2].minor.yy173;
- delete yymsp[0].minor.yy319;
+ yymsp[-2].minor.yy336->append((yymsp[0].minor.yy255)->mid(1)); // mid(1) to skip the first whitespace added in vtabarg
+ yygotominor.yy336 = yymsp[-2].minor.yy336;
+ delete yymsp[0].minor.yy255;
DONT_INHERIT_TOKENS("vtabarglist");
}
break;
- case 439: /* vtabarg ::= vtabarg vtabargtoken */
+ case 442: /* vtabarg ::= vtabarg vtabargtoken */
{
- yymsp[-1].minor.yy319->append(" "+ *(yymsp[0].minor.yy319));
- yygotominor.yy319 = yymsp[-1].minor.yy319;
- delete yymsp[0].minor.yy319;
+ yymsp[-1].minor.yy255->append(" "+ *(yymsp[0].minor.yy255));
+ yygotominor.yy255 = yymsp[-1].minor.yy255;
+ delete yymsp[0].minor.yy255;
}
break;
- case 440: /* vtabargtoken ::= ANY */
+ case 443: /* vtabargtoken ::= ANY */
{
- yygotominor.yy319 = new QString(yymsp[0].minor.yy0->value);
+ yygotominor.yy255 = new QString(yymsp[0].minor.yy0->value);
}
break;
- case 441: /* vtabargtoken ::= LP anylist RP */
+ case 444: /* vtabargtoken ::= LP anylist RP */
{
- yygotominor.yy319 = new QString("(");
- yygotominor.yy319->append(*(yymsp[-1].minor.yy319));
- yygotominor.yy319->append(")");
- delete yymsp[-1].minor.yy319;
+ yygotominor.yy255 = new QString("(");
+ yygotominor.yy255->append(*(yymsp[-1].minor.yy255));
+ yygotominor.yy255->append(")");
+ delete yymsp[-1].minor.yy255;
}
break;
- case 443: /* anylist ::= anylist LP anylist RP */
+ case 446: /* anylist ::= anylist LP anylist RP */
{
- yygotominor.yy319 = yymsp[-3].minor.yy319;
- yygotominor.yy319->append("(");
- yygotominor.yy319->append(*(yymsp[-1].minor.yy319));
- yygotominor.yy319->append(")");
- delete yymsp[-1].minor.yy319;
+ yygotominor.yy255 = yymsp[-3].minor.yy255;
+ yygotominor.yy255->append("(");
+ yygotominor.yy255->append(*(yymsp[-1].minor.yy255));
+ yygotominor.yy255->append(")");
+ delete yymsp[-1].minor.yy255;
DONT_INHERIT_TOKENS("anylist");
}
break;
- case 444: /* anylist ::= anylist ANY */
+ case 447: /* anylist ::= anylist ANY */
{
- yygotominor.yy319 = yymsp[-1].minor.yy319;
- yygotominor.yy319->append(yymsp[0].minor.yy0->value);
+ yygotominor.yy255 = yymsp[-1].minor.yy255;
+ yygotominor.yy255->append(yymsp[0].minor.yy0->value);
DONT_INHERIT_TOKENS("anylist");
}
break;
- case 445: /* with ::= */
-{yygotominor.yy161 = nullptr;}
+ case 448: /* with ::= */
+{yygotominor.yy321 = nullptr;}
break;
- case 446: /* with ::= WITH wqlist */
+ case 449: /* with ::= WITH wqlist */
{
- yygotominor.yy161 = new SqliteWith();
- yygotominor.yy161->cteList = *(yymsp[0].minor.yy164);
- delete yymsp[0].minor.yy164;
- objectForTokens = yygotominor.yy161;
+ yygotominor.yy321 = new SqliteWith();
+ yygotominor.yy321->cteList = *(yymsp[0].minor.yy17);
+ delete yymsp[0].minor.yy17;
+ objectForTokens = yygotominor.yy321;
}
break;
- case 447: /* with ::= WITH RECURSIVE wqlist */
+ case 450: /* with ::= WITH RECURSIVE wqlist */
{
- yygotominor.yy161 = new SqliteWith();
- yygotominor.yy161->cteList = *(yymsp[0].minor.yy164);
- yygotominor.yy161->recursive = true;
- delete yymsp[0].minor.yy164;
- objectForTokens = yygotominor.yy161;
+ yygotominor.yy321 = new SqliteWith();
+ yygotominor.yy321->cteList = *(yymsp[0].minor.yy17);
+ yygotominor.yy321->recursive = true;
+ delete yymsp[0].minor.yy17;
+ objectForTokens = yygotominor.yy321;
}
break;
- case 448: /* wqas ::= AS */
-{yygotominor.yy21 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::ANY);}
+ case 451: /* wqas ::= AS */
+{yygotominor.yy383 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::ANY);}
break;
- case 449: /* wqas ::= AS MATERIALIZED */
-{yygotominor.yy21 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::MATERIALIZED);}
+ case 452: /* wqas ::= AS MATERIALIZED */
+{yygotominor.yy383 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::MATERIALIZED);}
break;
- case 450: /* wqas ::= AS NOT MATERIALIZED */
-{yygotominor.yy21 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::NOT_MATERIALIZED);}
+ case 453: /* wqas ::= AS NOT MATERIALIZED */
+{yygotominor.yy383 = new SqliteWith::CommonTableExpression::AsMode(SqliteWith::CommonTableExpression::NOT_MATERIALIZED);}
break;
- case 451: /* wqlist ::= wqcte */
+ case 454: /* wqlist ::= wqcte */
{
- yygotominor.yy164 = new ParserCteList();
- yygotominor.yy164->append(yymsp[0].minor.yy146);
+ yygotominor.yy17 = new ParserCteList();
+ yygotominor.yy17->append(yymsp[0].minor.yy366);
}
break;
- case 452: /* wqlist ::= wqlist COMMA wqcte */
+ case 455: /* wqlist ::= wqlist COMMA wqcte */
{
- yygotominor.yy164 = yymsp[-2].minor.yy164;
- yygotominor.yy164->append(yymsp[0].minor.yy146);
+ yygotominor.yy17 = yymsp[-2].minor.yy17;
+ yygotominor.yy17->append(yymsp[0].minor.yy366);
DONT_INHERIT_TOKENS("wqlist");
}
break;
- case 453: /* wqlist ::= ID_TAB_NEW */
+ case 456: /* wqlist ::= ID_TAB_NEW */
{
parserContext->minorErrorBeforeNextToken("Syntax error");
}
break;
- case 454: /* wqcte ::= nm idxlist_opt wqas LP select RP */
+ case 457: /* wqcte ::= nm idxlist_opt wqas LP select RP */
{
- yygotominor.yy146 = new SqliteWith::CommonTableExpression(*(yymsp[-5].minor.yy319), *(yymsp[-4].minor.yy627), yymsp[-1].minor.yy297, *(yymsp[-3].minor.yy21));
- delete yymsp[-5].minor.yy319;
- delete yymsp[-4].minor.yy627;
- delete yymsp[-3].minor.yy21;
- objectForTokens = yygotominor.yy146;
+ yygotominor.yy366 = new SqliteWith::CommonTableExpression(*(yymsp[-5].minor.yy255), *(yymsp[-4].minor.yy527), yymsp[-1].minor.yy73, *(yymsp[-3].minor.yy383));
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-4].minor.yy527;
+ delete yymsp[-3].minor.yy383;
+ objectForTokens = yygotominor.yy366;
}
break;
- case 455: /* windowdefn_list ::= windowdefn */
+ case 458: /* windowdefn_list ::= windowdefn */
{
- yygotominor.yy525 = new ParserWindowDefList();
- yygotominor.yy525->append(yymsp[0].minor.yy562);
+ yygotominor.yy555 = new ParserWindowDefList();
+ yygotominor.yy555->append(yymsp[0].minor.yy74);
}
break;
- case 456: /* windowdefn_list ::= windowdefn_list COMMA windowdefn */
+ case 459: /* windowdefn_list ::= windowdefn_list COMMA windowdefn */
{
- yymsp[-2].minor.yy525->append(yymsp[0].minor.yy562);
- yygotominor.yy525 = yymsp[-2].minor.yy525;
+ yymsp[-2].minor.yy555->append(yymsp[0].minor.yy74);
+ yygotominor.yy555 = yymsp[-2].minor.yy555;
DONT_INHERIT_TOKENS("windowdefn_list");
}
break;
- case 457: /* windowdefn ::= nm AS LP window RP */
+ case 460: /* windowdefn ::= nm AS LP window RP */
{
- yygotominor.yy562 = new SqliteWindowDefinition(*(yymsp[-4].minor.yy319), yymsp[-1].minor.yy162);
- delete yymsp[-4].minor.yy319;
- objectForTokens = yygotominor.yy562;
+ yygotominor.yy74 = new SqliteWindowDefinition(*(yymsp[-4].minor.yy255), yymsp[-1].minor.yy14);
+ delete yymsp[-4].minor.yy255;
+ objectForTokens = yygotominor.yy74;
}
break;
- case 458: /* window ::= PARTITION BY nexprlist orderby_opt frame_opt */
+ case 461: /* window ::= PARTITION BY nexprlist orderby_opt frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->initPartitionBy(QString(), *(yymsp[-2].minor.yy615), *(yymsp[-1].minor.yy226), yymsp[0].minor.yy149);
- delete yymsp[-2].minor.yy615;
- delete yymsp[-1].minor.yy226;
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->initPartitionBy(QString(), *(yymsp[-2].minor.yy567), *(yymsp[-1].minor.yy499), yymsp[0].minor.yy585);
+ delete yymsp[-2].minor.yy567;
+ delete yymsp[-1].minor.yy499;
+ objectForTokens = yygotominor.yy14;
}
break;
- case 459: /* window ::= nm PARTITION BY nexprlist orderby_opt frame_opt */
+ case 462: /* window ::= nm PARTITION BY nexprlist orderby_opt frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->initPartitionBy(*(yymsp[-5].minor.yy319), *(yymsp[-2].minor.yy615), *(yymsp[-1].minor.yy226), yymsp[0].minor.yy149);
- delete yymsp[-2].minor.yy615;
- delete yymsp[-5].minor.yy319;
- delete yymsp[-1].minor.yy226;
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->initPartitionBy(*(yymsp[-5].minor.yy255), *(yymsp[-2].minor.yy567), *(yymsp[-1].minor.yy499), yymsp[0].minor.yy585);
+ delete yymsp[-2].minor.yy567;
+ delete yymsp[-5].minor.yy255;
+ delete yymsp[-1].minor.yy499;
+ objectForTokens = yygotominor.yy14;
}
break;
- case 460: /* window ::= ORDER BY sortlist frame_opt */
+ case 463: /* window ::= ORDER BY sortlist frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->initOrderBy(QString(), *(yymsp[-1].minor.yy226), yymsp[0].minor.yy149);
- delete yymsp[-1].minor.yy226;
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->initOrderBy(QString(), *(yymsp[-1].minor.yy499), yymsp[0].minor.yy585);
+ delete yymsp[-1].minor.yy499;
+ objectForTokens = yygotominor.yy14;
}
break;
- case 461: /* window ::= nm ORDER BY sortlist frame_opt */
+ case 464: /* window ::= nm ORDER BY sortlist frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->initOrderBy(*(yymsp[-4].minor.yy319), *(yymsp[-1].minor.yy226), yymsp[0].minor.yy149);
- delete yymsp[-1].minor.yy226;
- delete yymsp[-4].minor.yy319;
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->initOrderBy(*(yymsp[-4].minor.yy255), *(yymsp[-1].minor.yy499), yymsp[0].minor.yy585);
+ delete yymsp[-1].minor.yy499;
+ delete yymsp[-4].minor.yy255;
+ objectForTokens = yygotominor.yy14;
}
break;
- case 462: /* window ::= frame_opt */
+ case 465: /* window ::= frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->init(QString(), yymsp[0].minor.yy149);
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->init(QString(), yymsp[0].minor.yy585);
+ objectForTokens = yygotominor.yy14;
}
break;
- case 463: /* window ::= nm frame_opt */
+ case 466: /* window ::= nm frame_opt */
{
- yygotominor.yy162 = new SqliteWindowDefinition::Window();
- yygotominor.yy162->init(QString(), yymsp[0].minor.yy149);
- delete yymsp[-1].minor.yy319;
- objectForTokens = yygotominor.yy162;
+ yygotominor.yy14 = new SqliteWindowDefinition::Window();
+ yygotominor.yy14->init(QString(), yymsp[0].minor.yy585);
+ delete yymsp[-1].minor.yy255;
+ objectForTokens = yygotominor.yy14;
}
break;
- case 464: /* frame_opt ::= */
-{yygotominor.yy149 = nullptr;}
+ case 467: /* frame_opt ::= */
+{yygotominor.yy585 = nullptr;}
break;
- case 465: /* frame_opt ::= range_or_rows frame_bound_s frame_exclude_opt */
+ case 468: /* frame_opt ::= range_or_rows frame_bound_s frame_exclude_opt */
{
- yygotominor.yy149 = new SqliteWindowDefinition::Window::Frame(*(yymsp[-2].minor.yy143), yymsp[-1].minor.yy285, nullptr, *(yymsp[0].minor.yy237));
- delete yymsp[-2].minor.yy143;
- delete yymsp[0].minor.yy237;
- objectForTokens = yygotominor.yy149;
+ yygotominor.yy585 = new SqliteWindowDefinition::Window::Frame(*(yymsp[-2].minor.yy34), yymsp[-1].minor.yy394, nullptr, *(yymsp[0].minor.yy337));
+ delete yymsp[-2].minor.yy34;
+ delete yymsp[0].minor.yy337;
+ objectForTokens = yygotominor.yy585;
}
break;
- case 466: /* frame_opt ::= range_or_rows BETWEEN frame_bound_s AND frame_bound_e frame_exclude_opt */
+ case 469: /* frame_opt ::= range_or_rows BETWEEN frame_bound_s AND frame_bound_e frame_exclude_opt */
{
- yygotominor.yy149 = new SqliteWindowDefinition::Window::Frame(*(yymsp[-5].minor.yy143), yymsp[-3].minor.yy285, yymsp[-1].minor.yy285, *(yymsp[0].minor.yy237));
- delete yymsp[-5].minor.yy143;
- delete yymsp[0].minor.yy237;
- objectForTokens = yygotominor.yy149;
+ yygotominor.yy585 = new SqliteWindowDefinition::Window::Frame(*(yymsp[-5].minor.yy34), yymsp[-3].minor.yy394, yymsp[-1].minor.yy394, *(yymsp[0].minor.yy337));
+ delete yymsp[-5].minor.yy34;
+ delete yymsp[0].minor.yy337;
+ objectForTokens = yygotominor.yy585;
}
break;
- case 467: /* range_or_rows ::= RANGE|ROWS|GROUPS */
+ case 470: /* range_or_rows ::= RANGE|ROWS|GROUPS */
{
- yygotominor.yy143 = new SqliteWindowDefinition::Window::Frame::RangeOrRows(
+ yygotominor.yy34 = new SqliteWindowDefinition::Window::Frame::RangeOrRows(
SqliteWindowDefinition::Window::Frame::toRangeOrRows(yymsp[0].minor.yy0->value)
);
}
break;
- case 468: /* frame_bound_s ::= frame_bound */
- case 470: /* frame_bound_e ::= frame_bound */ yytestcase(yyruleno==470);
+ case 471: /* frame_bound_s ::= frame_bound */
+ case 473: /* frame_bound_e ::= frame_bound */ yytestcase(yyruleno==473);
{
- yygotominor.yy285 = yymsp[0].minor.yy285;
- objectForTokens = yygotominor.yy285;
+ yygotominor.yy394 = yymsp[0].minor.yy394;
+ objectForTokens = yygotominor.yy394;
}
break;
- case 469: /* frame_bound_s ::= UNBOUNDED PRECEDING */
- case 471: /* frame_bound_e ::= UNBOUNDED FOLLOWING */ yytestcase(yyruleno==471);
- case 473: /* frame_bound ::= CURRENT ROW */ yytestcase(yyruleno==473);
+ case 472: /* frame_bound_s ::= UNBOUNDED PRECEDING */
+ case 474: /* frame_bound_e ::= UNBOUNDED FOLLOWING */ yytestcase(yyruleno==474);
+ case 476: /* frame_bound ::= CURRENT ROW */ yytestcase(yyruleno==476);
{
- yygotominor.yy285 = new SqliteWindowDefinition::Window::Frame::Bound(nullptr, yymsp[-1].minor.yy0->value + " " + yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy285;
+ yygotominor.yy394 = new SqliteWindowDefinition::Window::Frame::Bound(nullptr, yymsp[-1].minor.yy0->value + " " + yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy394;
}
break;
- case 472: /* frame_bound ::= expr PRECEDING|FOLLOWING */
+ case 475: /* frame_bound ::= expr PRECEDING|FOLLOWING */
{
- yygotominor.yy285 = new SqliteWindowDefinition::Window::Frame::Bound(yymsp[-1].minor.yy186, yymsp[0].minor.yy0->value);
- objectForTokens = yygotominor.yy285;
+ yygotominor.yy394 = new SqliteWindowDefinition::Window::Frame::Bound(yymsp[-1].minor.yy176, yymsp[0].minor.yy0->value);
+ objectForTokens = yygotominor.yy394;
}
break;
- case 474: /* frame_exclude_opt ::= */
+ case 477: /* frame_exclude_opt ::= */
{
- yygotominor.yy237 = new SqliteWindowDefinition::Window::Frame::Exclude(
+ yygotominor.yy337 = new SqliteWindowDefinition::Window::Frame::Exclude(
SqliteWindowDefinition::Window::Frame::Exclude::null
);
}
break;
- case 475: /* frame_exclude_opt ::= EXCLUDE frame_exclude */
+ case 478: /* frame_exclude_opt ::= EXCLUDE frame_exclude */
{
- yygotominor.yy237 = yymsp[0].minor.yy237;
+ yygotominor.yy337 = yymsp[0].minor.yy337;
}
break;
- case 476: /* frame_exclude ::= NO OTHERS */
+ case 479: /* frame_exclude ::= NO OTHERS */
{
- yygotominor.yy237 = new SqliteWindowDefinition::Window::Frame::Exclude(
+ yygotominor.yy337 = new SqliteWindowDefinition::Window::Frame::Exclude(
SqliteWindowDefinition::Window::Frame::Exclude::NO_OTHERS
);
}
break;
- case 477: /* frame_exclude ::= CURRENT ROW */
+ case 480: /* frame_exclude ::= CURRENT ROW */
{
- yygotominor.yy237 = new SqliteWindowDefinition::Window::Frame::Exclude(
+ yygotominor.yy337 = new SqliteWindowDefinition::Window::Frame::Exclude(
SqliteWindowDefinition::Window::Frame::Exclude::CURRENT_ROW
);
}
break;
- case 478: /* frame_exclude ::= GROUP */
+ case 481: /* frame_exclude ::= GROUP */
{
- yygotominor.yy237 = new SqliteWindowDefinition::Window::Frame::Exclude(
+ yygotominor.yy337 = new SqliteWindowDefinition::Window::Frame::Exclude(
SqliteWindowDefinition::Window::Frame::Exclude::GROUP
);
}
break;
- case 479: /* frame_exclude ::= TIES */
+ case 482: /* frame_exclude ::= TIES */
{
- yygotominor.yy237 = new SqliteWindowDefinition::Window::Frame::Exclude(
+ yygotominor.yy337 = new SqliteWindowDefinition::Window::Frame::Exclude(
SqliteWindowDefinition::Window::Frame::Exclude::TIES
);
}
break;
- case 480: /* window_clause ::= WINDOW windowdefn_list */
+ case 483: /* window_clause ::= WINDOW windowdefn_list */
{
- yygotominor.yy525 = yymsp[0].minor.yy525;
+ yygotominor.yy555 = yymsp[0].minor.yy555;
}
break;
- case 481: /* filter_over ::= filter_clause over_clause */
+ case 484: /* filter_over ::= filter_clause over_clause */
{
- yygotominor.yy181 = new SqliteFilterOver(yymsp[-1].minor.yy39, yymsp[0].minor.yy11);
- objectForTokens = yygotominor.yy181;
+ yygotominor.yy487 = new SqliteFilterOver(yymsp[-1].minor.yy269, yymsp[0].minor.yy231);
+ objectForTokens = yygotominor.yy487;
}
break;
- case 482: /* filter_over ::= over_clause */
+ case 485: /* filter_over ::= over_clause */
{
- yygotominor.yy181 = new SqliteFilterOver(nullptr, yymsp[0].minor.yy11);
- objectForTokens = yygotominor.yy181;
+ yygotominor.yy487 = new SqliteFilterOver(nullptr, yymsp[0].minor.yy231);
+ objectForTokens = yygotominor.yy487;
}
break;
- case 483: /* filter_over ::= filter_clause */
+ case 486: /* filter_over ::= filter_clause */
{
- yygotominor.yy181 = new SqliteFilterOver(yymsp[0].minor.yy39, nullptr);
- objectForTokens = yygotominor.yy181;
+ yygotominor.yy487 = new SqliteFilterOver(yymsp[0].minor.yy269, nullptr);
+ objectForTokens = yygotominor.yy487;
}
break;
- case 484: /* over_clause ::= OVER LP window RP */
+ case 487: /* over_clause ::= OVER LP window RP */
{
- yygotominor.yy11 = new SqliteFilterOver::Over(yymsp[-1].minor.yy162);
- objectForTokens = yygotominor.yy11;
+ yygotominor.yy231 = new SqliteFilterOver::Over(yymsp[-1].minor.yy14);
+ objectForTokens = yygotominor.yy231;
}
break;
- case 485: /* over_clause ::= OVER nm */
+ case 488: /* over_clause ::= OVER nm */
{
- yygotominor.yy11 = new SqliteFilterOver::Over(*(yymsp[0].minor.yy319));
- delete yymsp[0].minor.yy319;
- objectForTokens = yygotominor.yy11;
+ yygotominor.yy231 = new SqliteFilterOver::Over(*(yymsp[0].minor.yy255));
+ delete yymsp[0].minor.yy255;
+ objectForTokens = yygotominor.yy231;
}
break;
- case 486: /* filter_clause ::= FILTER LP WHERE expr RP */
+ case 489: /* filter_clause ::= FILTER LP WHERE expr RP */
{
- yygotominor.yy39 = new SqliteFilterOver::Filter(yymsp[-1].minor.yy186);
- objectForTokens = yygotominor.yy39;
+ yygotominor.yy269 = new SqliteFilterOver::Filter(yymsp[-1].minor.yy176);
+ objectForTokens = yygotominor.yy269;
}
break;
default:
diff --git a/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.y b/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.y
index 4b1dda4..0e50178 100644
--- a/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.y
+++ b/SQLiteStudio3/coreSQLiteStudio/parser/sqlite3_parse.y
@@ -1566,6 +1566,27 @@ insert_stmt(X) ::= with(W) insert_cmd(C)
objectForTokens = X;
}
+
+insert_stmt(X) ::= with(W) insert_cmd(C)
+ INTO fullname(N)
+ LP idlist(I) rp_opt(R). {
+ parserContext->minorErrorBeforeNextToken("Syntax error");
+ X = new SqliteInsert(
+ C->replace,
+ C->orConflict,
+ N->name1,
+ N->name2,
+ *(I),
+ W,
+ QList<SqliteResultColumn*>()
+ );
+ objectForTokens = X;
+ delete N;
+ delete I;
+ delete C;
+ delete R;
+ }
+
insert_stmt(X) ::= with(W) insert_cmd(C)
INTO. {
parserContext->minorErrorBeforeNextToken("Syntax error");
@@ -1964,6 +1985,12 @@ expr(X) ::= exprx(E). {X = E;}
not_opt(X) ::= . {X = new bool(false);}
not_opt(X) ::= NOT. {X = new bool(true);}
+%type rp_opt {bool*}
+%destructor rp_opt {parser_safe_delete($$);}
+rp_opt(X) ::= . {X = new bool(false);}
+rp_opt(X) ::= RP. {X = new bool(true);}
+
+
%type likeop {SqliteExpr::LikeOp*}
%destructor likeop {parser_safe_delete($$);}
likeop(X) ::= LIKE_KW|MATCH(T). {X = new SqliteExpr::LikeOp(SqliteExpr::likeOp(T->value));}
diff --git a/SQLiteStudio3/coreSQLiteStudio/plugins/scriptingsql.cpp b/SQLiteStudio3/coreSQLiteStudio/plugins/scriptingsql.cpp
index 7edd7e7..47aabfc 100644
--- a/SQLiteStudio3/coreSQLiteStudio/plugins/scriptingsql.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/plugins/scriptingsql.cpp
@@ -3,6 +3,7 @@
#include "db/db.h"
#include "db/sqlquery.h"
#include "services/dbmanager.h"
+#include "common/utils_sql.h"
ScriptingSql::ScriptingSql()
{
@@ -58,7 +59,9 @@ QVariant ScriptingSql::evaluate(ScriptingPlugin::Context* context, const QString
QString sql = code;
if (ctx->variables.size() > 0)
{
- for (const QString& key : ctx->variables.keys())
+ QList<QString> keys = ctx->variables.keys();
+ std::sort(keys.begin(), keys.end(), std::greater<QString>());
+ for (const QString& key : keys)
{
QString value = "'" + ctx->variables[key].toString() + "'";
sql.replace(":" + key, value).replace("@" + key, value).replace("$" + key, value);
@@ -151,15 +154,26 @@ void ScriptingSql::deinit()
void ScriptingSql::replaceNamedArgs(QString& sql, const ScriptingPlugin::FunctionInfo& funcInfo, const QList<QVariant>& args)
{
+ // First build map of argName to its value in order in which arguments were passed to the function
int i = 0;
- for (const QString& key : funcInfo.getArguments())
+ QStringList argNames = funcInfo.getArguments();
+ QHash<QString, QString> argMap;
+ for (const QString& argName : argNames)
{
if (i >= args.size())
break;
- QString value = "'" + args[i++].toString() + "'";
- sql.replace(":" + key, value)
- .replace("@" + key, value)
- .replace("$" + key, value);
+ argMap[argName] = valueToSqlLiteral(args[i++]);
+ }
+
+ // Then sort arguments in alphabetically descending order, to prevent replacing shorter names first
+ // and proceed with argument substitutions
+ std::sort(argNames.begin(), argNames.end(), std::greater<QString>());
+ for (const QString& argName : argNames)
+ {
+ QString value = argMap[argName];
+ sql.replace(":" + argName, value)
+ .replace("@" + argName, value)
+ .replace("$" + argName, value);
}
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/schemaresolver.cpp b/SQLiteStudio3/coreSQLiteStudio/schemaresolver.cpp
index 129bb43..324cbf4 100644
--- a/SQLiteStudio3/coreSQLiteStudio/schemaresolver.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/schemaresolver.cpp
@@ -190,6 +190,33 @@ QStringList SchemaResolver::getTableColumns(const QString &database, const QStri
return columns;
}
+StrHash<DataType> SchemaResolver::getTableColumnDataTypesByName(const QString &table)
+{
+ return getTableColumnDataTypesByName("main", table);
+}
+
+StrHash<DataType> SchemaResolver::getTableColumnDataTypesByName(const QString &database, const QString &table)
+{
+ StrHash<DataType> dataTypes;
+ SqliteCreateTablePtr createTable = getParsedObject(database, table, TABLE).dynamicCast<SqliteCreateTable>();
+ if (!createTable)
+ {
+ return dataTypes;
+ }
+
+ for (SqliteCreateTable::Column* col : createTable->columns)
+ {
+ if (!col->type)
+ {
+ dataTypes[col->name] = DataType();
+ continue;
+ }
+
+ dataTypes[col->name] = col->type->toDataType();
+ }
+ return dataTypes;
+}
+
QList<DataType> SchemaResolver::getTableColumnDataTypes(const QString& table, int expectedNumberOfTypes)
{
return getTableColumnDataTypes("main", table, expectedNumberOfTypes);
@@ -806,56 +833,52 @@ QStringList SchemaResolver::getFkReferencingTables(const QString& table)
QStringList SchemaResolver::getFkReferencingTables(const QString& database, const QString& table)
{
- // Get all tables
- StrHash<SqliteCreateTablePtr> parsedTables = getAllParsedTables(database);
+ static_qstring(fkQueryTpl, R"(
+ WITH foreign_keys AS (
+ SELECT m.name AS table_name, lower(fk.[table]) AS foreign_table
+ FROM %1.sqlite_master AS m
+ JOIN %1.pragma_foreign_key_list(m.name) AS fk
+ WHERE m.type = 'table'
+ )
+ SELECT table_name
+ FROM foreign_keys
+ WHERE foreign_table = '%2';)");
+
+ SqlQueryPtr results = db->exec(fkQueryTpl.arg(getPrefixDb(database), escapeString(table.toLower())), dbFlags);
+ if (results->isError())
+ {
+ qCritical() << "Error while getting FK-referencing table list in SchemaResolver:" << results->getErrorCode();
+ return QStringList();
+ }
- // Exclude queried table from the list
- parsedTables.remove(table);
+ QStringList resList;
+ for (SqlResultsRowPtr row : results->getAll())
+ resList << row->value(0).toString();
- // Resolve referencing tables
- return getFkReferencingTables(table, parsedTables.values());
+ return resList;
}
-QStringList SchemaResolver::getFkReferencingTables(const QString& table, const QList<SqliteCreateTablePtr>& allParsedTables)
+QStringList SchemaResolver::getFkReferencedTables(const QString& table)
{
- QStringList tables;
-
- QList<SqliteCreateTable::Constraint*> tableFks;
- QList<SqliteCreateTable::Column::Constraint*> fks;
- bool result = false;
- for (SqliteCreateTablePtr createTable : allParsedTables)
- {
- // Check table constraints
- tableFks = createTable->getForeignKeysByTable(table);
- result = contains<SqliteCreateTable::Constraint*>(tableFks, [&table](SqliteCreateTable::Constraint* fk)
- {
- return fk->foreignKey->foreignTable == table;
- });
-
- if (result)
- {
- tables << createTable->table;
- continue;
- }
+ return getFkReferencedTables("main", table);
+}
- // Check column constraints
- for (SqliteCreateTable::Column* column : createTable->columns)
- {
- fks = column->getForeignKeysByTable(table);
- result = contains<SqliteCreateTable::Column::Constraint*>(fks, [&table](SqliteCreateTable::Column::Constraint* fk)
- {
- return fk->foreignKey->foreignTable == table;
- });
+QStringList SchemaResolver::getFkReferencedTables(const QString& database, const QString& table)
+{
+ static_qstring(fkQueryTpl, "SELECT [table] FROM %1.pragma_foreign_key_list('%2');");
- if (result)
- {
- tables << createTable->table;
- break;
- }
- }
+ SqlQueryPtr results = db->exec(fkQueryTpl.arg(getPrefixDb(database), escapeString(table)), dbFlags);
+ if (results->isError())
+ {
+ qCritical() << "Error while getting FK-referenced table list in SchemaResolver:" << results->getErrorCode() << results->getErrorText();
+ return QStringList();
}
- return tables;
+ QStringList resList;
+ for (SqlResultsRowPtr row : results->getAll())
+ resList << row->value(0).toString();
+
+ return resList;
}
SchemaResolver::ObjectType SchemaResolver::objectTypeFromQueryType(const SqliteQueryType& queryType)
@@ -901,9 +924,9 @@ SchemaResolver::ObjectType SchemaResolver::objectTypeFromQueryType(const SqliteQ
QStringList SchemaResolver::getIndexesForTable(const QString& database, const QString& table)
{
- static_qstring(idxForTableTpl, "SELECT name FROM %1.pragma_index_list(%2)");
+ static_qstring(idxForTableTpl, "SELECT name FROM %1.sqlite_master WHERE type = 'index' AND (tbl_name = '%2' OR lower(tbl_name) = lower('%2'));");
- QString query = idxForTableTpl.arg(wrapObjName(database), wrapString(table));
+ QString query = idxForTableTpl.arg(wrapObjName(database), wrapObjIfNeeded(table));
SqlQueryPtr results = db->exec(query, dbFlags);
QStringList indexes;
@@ -927,9 +950,14 @@ QStringList SchemaResolver::getIndexesForTable(const QString& table)
QStringList SchemaResolver::getTriggersForTable(const QString& database, const QString& table)
{
+ static_qstring(trigForTableTpl, "SELECT name FROM %1.sqlite_master WHERE type = 'trigger' AND (tbl_name = '%2' OR lower(tbl_name) = lower('%2'));");
+
+ QString query = trigForTableTpl.arg(wrapObjName(database), escapeString(table));
+ SqlQueryPtr results = db->exec(query, dbFlags);
+
QStringList names;
- for (SqliteCreateTriggerPtr trig : getParsedTriggersForTable(database, table))
- names << trig->trigger;
+ for (SqlResultsRowPtr row : results->getAll())
+ names << row->value(0).toString();
return names;
}
@@ -967,6 +995,96 @@ QStringList SchemaResolver::getViewsForTable(const QString& table)
return getViewsForTable("main", table);
}
+QStringList SchemaResolver::getIndexDdlsForTable(const QString& database, const QString& table)
+{
+ return getObjectDdlsReferencingTableOrView(database, table, INDEX);
+}
+
+QStringList SchemaResolver::getIndexDdlsForTable(const QString& table)
+{
+ return getIndexDdlsForTable("main", table);
+}
+
+QStringList SchemaResolver::getTriggerDdlsForTableOrView(const QString& database, const QString& table)
+{
+ return getObjectDdlsReferencingTableOrView(database, table, TRIGGER);
+}
+
+QStringList SchemaResolver::getTriggerDdlsForTableOrView(const QString& table)
+{
+ return getTriggerDdlsForTableOrView("main", table);
+}
+
+QList<SchemaResolver::TableListItem> SchemaResolver::getAllTableListItems()
+{
+ return getAllTableListItems("main");
+}
+
+QList<SchemaResolver::TableListItem> SchemaResolver::getAllTableListItems(const QString& database)
+{
+ QList<TableListItem> items;
+
+ QList<QVariant> rows;
+ bool useCache = usesCache();
+ ObjectCacheKey key(ObjectCacheKey::TABLE_LIST_ITEM, db, database);
+ if (useCache && cache.contains(key))
+ {
+ rows = cache.object(key, true)->toList();
+ }
+ else
+ {
+ //SqlQueryPtr results = db->exec(QString("PRAGMA %1.table_list").arg(getPrefixDb(database)), dbFlags); // not using for now to support SQLite versions < 3.37.0
+ static_qstring(queryTpl, "SELECT name, (CASE WHEN type = 'view' THEN 'view' WHEN sql LIKE 'CREATE VIRTUAL%' THEN 'virtual' ELSE 'table' END) AS type FROM %1.sqlite_master WHERE type IN ('table', 'view')");
+ SqlQueryPtr results = db->exec(queryTpl.arg(getPrefixDb(database)), dbFlags);
+ if (results->isError())
+ {
+ qCritical() << "Error while getting all table list items in SchemaResolver:" << results->getErrorCode();
+ return items;
+ }
+
+ for (const SqlResultsRowPtr& row : results->getAll())
+ rows << row->valueMap();
+
+ if (!ignoreSystemObjects)
+ {
+ static QHash<QString, QVariant> sqliteMasterRow {
+ {"name", "sqlite_master"},
+ {"type", "table"}
+ };
+
+ static QHash<QString, QVariant> sqliteTempMasterRow {
+ {"name", "sqlite_temp_master"},
+ {"type", "table"}
+ };
+
+ rows << QVariant(sqliteMasterRow) << QVariant(sqliteTempMasterRow);
+ }
+
+ if (useCache)
+ cache.insert(key, new QVariant(rows));
+ }
+
+ QHash<QString, QVariant> row;
+ for (const QVariant& rowVariant : rows)
+ {
+ row = rowVariant.toHash();
+ QString value = row["name"].toString();
+ QString type = row["type"].toString();
+ if (isFilteredOut(value, type))
+ continue;
+
+ TableListItem item;
+ item.type = stringToTableListItemType(type);
+ if (item.type == TableListItem::UNKNOWN)
+ qCritical() << "Unhlandled table item type:" << type;
+
+ item.name = value;
+ items << item;
+ }
+
+ return items;
+}
+
StrHash<SchemaResolver::ObjectDetails> SchemaResolver::getAllObjectDetails()
{
return getAllObjectDetails("main");
@@ -974,13 +1092,13 @@ StrHash<SchemaResolver::ObjectDetails> SchemaResolver::getAllObjectDetails()
StrHash<SchemaResolver::ObjectDetails> SchemaResolver::getAllObjectDetails(const QString& database)
{
- StrHash< ObjectDetails> details;
+ StrHash<ObjectDetails> details;
ObjectDetails detail;
QString type;
QList<QVariant> rows;
bool useCache = usesCache();
- ObjectCacheKey key(ObjectCacheKey::OBJECT_DETAILS, db, database);
+ ObjectCacheKey key(ObjectCacheKey::OBJECT_DETAILS, db, ignoreSystemObjects, database);
if (useCache && cache.contains(key))
{
rows = cache.object(key, true)->toList();
@@ -995,7 +1113,12 @@ StrHash<SchemaResolver::ObjectDetails> SchemaResolver::getAllObjectDetails(const
}
for (const SqlResultsRowPtr& row : results->getAll())
+ {
+ if (isFilteredOut(row->value("name").toString(), row->value("type").toString()))
+ continue;
+
rows << row->valueMap();
+ }
if (useCache)
cache.insert(key, new QVariant(rows));
@@ -1019,27 +1142,33 @@ StrHash<SchemaResolver::ObjectDetails> SchemaResolver::getAllObjectDetails(const
QList<SqliteCreateIndexPtr> SchemaResolver::getParsedIndexesForTable(const QString& database, const QString& table)
{
- QList<SqliteCreateIndexPtr> createIndexList;
+ static_qstring(idxForTableTpl, "SELECT sql, name FROM %1.sqlite_master WHERE type = 'index' AND lower(tbl_name) = lower(?);");
- QStringList indexes = getIndexes(database);
- SqliteQueryPtr query;
- SqliteCreateIndexPtr createIndex;
- for (const QString& index : indexes)
+ QString query = idxForTableTpl.arg(getPrefixDb(database));
+ SqlQueryPtr results = db->exec(query, {table}, dbFlags);
+
+ QList<SqliteCreateIndexPtr> createIndexList;
+ for (SqlResultsRowPtr row : results->getAll())
{
- query = getParsedObject(database, index, INDEX);
+ QString ddl = row->value(0).toString();
+ QString name = row->value(1).toString();
+ if (ddl.isEmpty() || isFilteredOut(name, "index"))
+ continue;
+
+ SqliteQueryPtr query = getParsedDdl(ddl);
if (!query)
continue;
- createIndex = query.dynamicCast<SqliteCreateIndex>();
+ SqliteCreateIndexPtr createIndex = query.dynamicCast<SqliteCreateIndex>();
if (!createIndex)
{
- qWarning() << "Parsed DDL was not a CREATE INDEX statement, while queried for indexes.";
+ qWarning() << "Parsed DDL was not a CREATE INDEX statement, while queried for indexes. Queried db & table:"
+ << database << table << "Index name:" << name << "DDL:" << ddl;
continue;
}
-
- if (createIndex->table.compare(table, Qt::CaseInsensitive) == 0)
- createIndexList << createIndex;
+ createIndexList << createIndex;
}
+
return createIndexList;
}
@@ -1050,7 +1179,7 @@ QList<SqliteCreateIndexPtr> SchemaResolver::getParsedIndexesForTable(const QStri
QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForTable(const QString& database, const QString& table, bool includeContentReferences)
{
- return getParsedTriggersForTableOrView(database, table, includeContentReferences, true);
+ return getParsedTriggersForTableOrView(database, table, includeContentReferences);
}
QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForTable(const QString& table, bool includeContentReferences)
@@ -1060,7 +1189,7 @@ QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForTable(const QS
QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForView(const QString& database, const QString& view, bool includeContentReferences)
{
- return getParsedTriggersForTableOrView(database, view, includeContentReferences, false);
+ return getParsedTriggersForTableOrView(database, view, includeContentReferences);
}
QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForView(const QString& view, bool includeContentReferences)
@@ -1069,40 +1198,88 @@ QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForView(const QSt
}
QList<SqliteCreateTriggerPtr> SchemaResolver::getParsedTriggersForTableOrView(const QString& database, const QString& tableOrView,
- bool includeContentReferences, bool table)
+ bool includeContentReferences)
{
- QList<SqliteCreateTriggerPtr> createTriggerList;
+ static_qstring(trigForTableTpl, "SELECT sql, name FROM %1.sqlite_master WHERE type = 'trigger' AND lower(tbl_name) = lower('%2');");
+ static_qstring(allTrigTpl, "SELECT sql FROM %1.sqlite_master WHERE type = 'trigger' AND lower(name) NOT IN (%2);");
- QStringList triggers = getTriggers(database);
- SqliteQueryPtr query;
- SqliteCreateTriggerPtr createTrigger;
- for (const QString& trig : triggers)
+ QString query = trigForTableTpl.arg(getPrefixDb(database), escapeString(tableOrView));
+ SqlQueryPtr results = db->exec(query, dbFlags);
+
+ QStringList alreadyProcessed;
+ QList<SqliteCreateTriggerPtr> createTriggerList;
+ for (SqlResultsRowPtr row : results->getAll())
{
- query = getParsedObject(database, trig, TRIGGER);
- if (!query)
+ alreadyProcessed << wrapString(escapeString(row->value(1).toString().toLower()));
+ SqliteQueryPtr parsedDdl = getParsedDdl(row->value(0).toString());
+ if (!parsedDdl)
continue;
- createTrigger = query.dynamicCast<SqliteCreateTrigger>();
+ SqliteCreateTriggerPtr createTrigger = parsedDdl.dynamicCast<SqliteCreateTrigger>();
if (!createTrigger)
{
- qWarning() << "Parsed DDL was not a CREATE TRIGGER statement, while queried for triggers." << createTrigger.data();
+ qWarning() << "Parsed DDL was not a CREATE TRIGGER statement, while queried for triggers.";
continue;
}
+ createTriggerList << createTrigger;
+ }
- // The condition below checks:
- // 1. if this is a call for table triggers and event time is INSTEAD_OF - skip this iteration
- // 2. if this is a call for view triggers and event time is _not_ INSTEAD_OF - skip this iteration
- // In other words, it's a logical XOR for "table" flag and "eventTime == INSTEAD_OF" condition.
- if (table == (createTrigger->eventTime == SqliteCreateTrigger::Time::INSTEAD_OF))
- continue;
+ if (includeContentReferences)
+ {
+ query = allTrigTpl.arg(wrapObjName(database), alreadyProcessed.join(", "));
+ results = db->exec(query, dbFlags);
- if (createTrigger->table.compare(tableOrView, Qt::CaseInsensitive) == 0)
- createTriggerList << createTrigger;
- else if (includeContentReferences && indexOf(createTrigger->getContextTables(), tableOrView, Qt::CaseInsensitive) > -1)
- createTriggerList << createTrigger;
+ for (SqlResultsRowPtr row : results->getAll())
+ {
+ SqliteQueryPtr parsedDdl = getParsedDdl(row->value(0).toString());
+ if (!parsedDdl)
+ continue;
+ SqliteCreateTriggerPtr createTrigger = parsedDdl.dynamicCast<SqliteCreateTrigger>();
+ if (!createTrigger)
+ {
+ qWarning() << "Parsed DDL was not a CREATE TRIGGER statement, while queried for triggers.";
+ continue;
+ }
+ if (indexOf(createTrigger->getContextTables(), tableOrView, Qt::CaseInsensitive) > -1)
+ createTriggerList << createTrigger;
+ }
}
+
return createTriggerList;
+
+// QList<SqliteCreateTriggerPtr> createTriggerList;
+
+// QStringList triggers = getTriggersForTable(database);
+// SqliteQueryPtr query;
+// SqliteCreateTriggerPtr createTrigger;
+// for (const QString& trig : triggers)
+// {
+// query = getParsedObject(database, trig, TRIGGER);
+// if (!query)
+// continue;
+
+// createTrigger = query.dynamicCast<SqliteCreateTrigger>();
+// if (!createTrigger)
+// {
+// qWarning() << "Parsed DDL was not a CREATE TRIGGER statement, while queried for triggers." << createTrigger.data();
+// continue;
+// }
+
+// // The condition below checks:
+// // 1. if this is a call for table triggers and event time is INSTEAD_OF - skip this iteration
+// // 2. if this is a call for view triggers and event time is _not_ INSTEAD_OF - skip this iteration
+// // In other words, it's a logical XOR for "table" flag and "eventTime == INSTEAD_OF" condition.
+// if (table == (createTrigger->eventTime == SqliteCreateTrigger::Time::INSTEAD_OF))
+// continue;
+
+// if (createTrigger->table.compare(tableOrView, Qt::CaseInsensitive) == 0)
+// createTriggerList << createTrigger;
+// else if (includeContentReferences && indexOf(createTrigger->getContextTables(), tableOrView, Qt::CaseInsensitive) > -1)
+// createTriggerList << createTrigger;
+
+// }
+// return createTriggerList;
}
QString SchemaResolver::objectTypeToString(SchemaResolver::ObjectType type)
@@ -1137,6 +1314,20 @@ SchemaResolver::ObjectType SchemaResolver::stringToObjectType(const QString& typ
return SchemaResolver::ANY;
}
+SchemaResolver::TableListItem::Type SchemaResolver::stringToTableListItemType(const QString& type)
+{
+ if (type == "table")
+ return SchemaResolver::TableListItem::TABLE;
+ else if (type == "virtual")
+ return SchemaResolver::TableListItem::VIRTUAL_TABLE;
+ else if (type == "shadow")
+ return SchemaResolver::TableListItem::SHADOW_TABLE;
+ else if (type == "view")
+ return SchemaResolver::TableListItem::VIEW;
+ else
+ return SchemaResolver::TableListItem::UNKNOWN;
+}
+
void SchemaResolver::staticInit()
{
cache.setExpireTime(3000);
@@ -1208,12 +1399,8 @@ bool SchemaResolver::isWithoutRowIdTable(const QString& database, const QString&
bool SchemaResolver::isVirtualTable(const QString& database, const QString& table)
{
- SqliteQueryPtr query = getParsedObject(database, table, TABLE);
- if (!query)
- return false;
-
- SqliteCreateVirtualTablePtr createVirtualTable = query.dynamicCast<SqliteCreateVirtualTable>();
- return !createVirtualTable.isNull();
+ QString ddl = getObjectDdl(database, table, TABLE);
+ return ddl.simplified().toUpper().startsWith("CREATE VIRTUAL TABLE");
}
bool SchemaResolver::isVirtualTable(const QString& table)
@@ -1331,17 +1518,50 @@ QString SchemaResolver::normalizeCaseObjectNameByQuery(const QString& query, con
return results->getSingleCell().toString();
}
+QStringList SchemaResolver::getObjectDdlsReferencingTableOrView(const QString& database, const QString& table, ObjectType type)
+{
+ static_qstring(trigForTableTpl, "SELECT sql FROM %1.sqlite_master WHERE type = '%3' AND (tbl_name = '%2' OR lower(tbl_name) = lower('%2'));"); // non-lower variant for cyrlic alphabet
+
+ QString query = trigForTableTpl.arg(wrapObjName(database), escapeString(table), objectTypeToString(type));
+ SqlQueryPtr results = db->exec(query, dbFlags);
+
+ QStringList ddls;
+ for (SqlResultsRowPtr row : results->getAll())
+ {
+ QString ddl = row->value(0).toString();
+ if (!ddl.trimmed().endsWith(";"))
+ ddl += ";";
+
+ ddls << ddl;
+ }
+
+ return ddls;
+
+}
+
SchemaResolver::ObjectCacheKey::ObjectCacheKey(Type type, Db* db, const QString& value1, const QString& value2, const QString& value3) :
- type(type), db(db), value1(value1), value2(value2), value3(value3)
+ ObjectCacheKey(type, db, false, value1, value2, value3)
+{
+}
+
+SchemaResolver::ObjectCacheKey::ObjectCacheKey(Type type, Db* db, bool skipSystemObj, const QString& value1, const QString& value2, const QString& value3) :
+ type(type), db(db), skipSystemObj(skipSystemObj), value1(value1), value2(value2), value3(value3)
{
}
int qHash(const SchemaResolver::ObjectCacheKey& key)
{
- return qHash(key.type) ^ qHash(key.db) ^ qHash(key.value1) ^ qHash(key.value2) ^ qHash(key.value3);
+ return qHash(key.type) ^ qHash(key.db) ^ qHash(key.value1) ^ qHash(key.value2) ^ qHash(key.value3) ^ qHash(key.skipSystemObj);
}
int operator==(const SchemaResolver::ObjectCacheKey& k1, const SchemaResolver::ObjectCacheKey& k2)
{
- return (k1.type == k2.type && k1.db == k2.db && k1.value1 == k2.value1 && k1.value2 == k2.value2 && k1.value3 == k2.value3);
+ return (
+ k1.type == k2.type &&
+ k1.db == k2.db &&
+ k1.value1 == k2.value1 &&
+ k1.value2 == k2.value2 &&
+ k1.value3 == k2.value3 &&
+ k1.skipSystemObj == k2.skipSystemObj
+ );
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/schemaresolver.h b/SQLiteStudio3/coreSQLiteStudio/schemaresolver.h
index cfb5bd5..c7b457f 100644
--- a/SQLiteStudio3/coreSQLiteStudio/schemaresolver.h
+++ b/SQLiteStudio3/coreSQLiteStudio/schemaresolver.h
@@ -40,19 +40,37 @@ class API_EXPORT SchemaResolver
QString ddl;
};
+ struct TableListItem
+ {
+ enum Type
+ {
+ TABLE,
+ VIRTUAL_TABLE,
+ SHADOW_TABLE,
+ VIEW,
+ UNKNOWN
+ };
+
+ Type type;
+ QString name;
+ };
+
struct ObjectCacheKey
{
enum Type
{
OBJECT_NAMES,
OBJECT_DETAILS,
+ TABLE_LIST_ITEM,
OBJECT_DDL
};
ObjectCacheKey(Type type, Db* db, const QString& value1 = QString(), const QString& value2 = QString(), const QString& value3 = QString());
+ ObjectCacheKey(Type type, Db* db, bool skipSystemObj, const QString& value1 = QString(), const QString& value2 = QString(), const QString& value3 = QString());
Type type;
Db* db;
+ bool skipSystemObj;
QString value1;
QString value2;
QString value3;
@@ -76,6 +94,8 @@ class API_EXPORT SchemaResolver
QString getUniqueName(const QString& namePrefix = QString(), const QStringList& forbiddenNames = QStringList());
QStringList getFkReferencingTables(const QString& table);
QStringList getFkReferencingTables(const QString& database, const QString& table);
+ QStringList getFkReferencedTables(const QString& table);
+ QStringList getFkReferencedTables(const QString& database, const QString& table);
QStringList getIndexesForTable(const QString& database, const QString& table);
QStringList getIndexesForTable(const QString& table);
@@ -85,6 +105,13 @@ class API_EXPORT SchemaResolver
QStringList getTriggersForView(const QString& view);
QStringList getViewsForTable(const QString& database, const QString& table);
QStringList getViewsForTable(const QString& table);
+ QStringList getIndexDdlsForTable(const QString& database, const QString& table);
+ QStringList getIndexDdlsForTable(const QString& table);
+ QStringList getTriggerDdlsForTableOrView(const QString& database, const QString& table);
+ QStringList getTriggerDdlsForTableOrView(const QString& table);
+
+ QList<TableListItem> getAllTableListItems();
+ QList<TableListItem> getAllTableListItems(const QString& database);
StrHash<ObjectDetails> getAllObjectDetails();
StrHash<ObjectDetails> getAllObjectDetails(const QString& database);
@@ -131,6 +158,8 @@ class API_EXPORT SchemaResolver
*/
QStringList getTableColumns(const QString& database, const QString& table, bool onlyReal = false);
+ StrHash<DataType> getTableColumnDataTypesByName(const QString& table);
+ StrHash<DataType> getTableColumnDataTypesByName(const QString& database, const QString& table);
QList<DataType> getTableColumnDataTypes(const QString& table, int expectedNumberOfTypes = -1);
QList<DataType> getTableColumnDataTypes(const QString& database, const QString& table, int expectedNumberOfTypes = -1);
@@ -180,7 +209,6 @@ class API_EXPORT SchemaResolver
QString getSqliteAutoIndexDdl(const QString& database, const QString& index);
static QString getSqliteMasterDdl(bool temp = false);
- static QStringList getFkReferencingTables(const QString& table, const QList<SqliteCreateTablePtr>& allParsedTables);
static ObjectType objectTypeFromQueryType(const SqliteQueryType& queryType);
QStringList getCollations();
@@ -196,6 +224,7 @@ class API_EXPORT SchemaResolver
static QString objectTypeToString(ObjectType type);
static ObjectType stringToObjectType(const QString& type);
+ static TableListItem::Type stringToTableListItemType(const QString& type);
static void staticInit();
static_char* USE_SCHEMA_CACHING = "useSchemaCaching";
@@ -207,11 +236,12 @@ class API_EXPORT SchemaResolver
StrHash< QStringList> getGroupedObjects(const QString &database, const QStringList& inputList, SqliteQueryType type);
bool isFilteredOut(const QString& value, const QString& type);
void filterSystemIndexes(QStringList& indexes);
- QList<SqliteCreateTriggerPtr> getParsedTriggersForTableOrView(const QString& database, const QString& tableOrView, bool includeContentReferences, bool table);
+ QList<SqliteCreateTriggerPtr> getParsedTriggersForTableOrView(const QString& database, const QString& tableOrView, bool includeContentReferences);
QString getObjectDdlWithDifficultName(const QString& dbName, const QString& lowerName, QString targetTable, ObjectType type);
QString getObjectDdlWithSimpleName(const QString& dbName, const QString& lowerName, QString targetTable, ObjectType type);
StrHash<QString> getIndexesWithTables(const QString& database = QString());
QString normalizeCaseObjectNameByQuery(const QString& query, const QString& name);
+ QStringList getObjectDdlsReferencingTableOrView(const QString& database, const QString& table, ObjectType type);
template <class T>
StrHash<QSharedPointer<T>> getAllParsedObjectsForType(const QString& database, const QString& type);
diff --git a/SQLiteStudio3/coreSQLiteStudio/selectresolver.cpp b/SQLiteStudio3/coreSQLiteStudio/selectresolver.cpp
index 8a3efa8..0e4dad5 100644
--- a/SQLiteStudio3/coreSQLiteStudio/selectresolver.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/selectresolver.cpp
@@ -110,7 +110,7 @@ QSet<SelectResolver::Table> SelectResolver::resolveTables(SqliteSelect::Core::Jo
QList<Column> columns = resolveAvailableColumns(joinSrc);
for (const Column& col : columns)
{
- if (col.type != Column::Type::COLUMN)
+ if (col.type != Column::Type::COLUMN || (col.flags & SelectResolver::FROM_RES_COL_SUBSELECT))
continue;
tables << col.getTable();
@@ -356,10 +356,13 @@ void SelectResolver::resolveStar(SqliteSelect::Core::ResultColumn *resCol)
}
// If source column name is aliased, use it
- if (!column.alias.isNull())
- column.displayName = column.alias;
- else
- column.displayName = column.column;
+ if (column.displayName.isNull())
+ {
+ if (!column.alias.isNull())
+ column.displayName = column.alias;
+ else
+ column.displayName = column.column;
+ }
currentCoreResults << column;
foundAtLeastOne = true;
@@ -379,8 +382,10 @@ void SelectResolver::resolveExpr(SqliteSelect::Core::ResultColumn *resCol)
column.alias = resCol->alias;
column.column = getResColTokensWithoutAlias(resCol).detokenize().trimmed();
column.displayName = !resCol->alias.isNull() ? column.alias : column.column;
-
column.type = Column::OTHER;
+ if (expr->mode == SqliteExpr::Mode::SUB_SELECT)
+ column.flags |= SelectResolver::FROM_RES_COL_SUBSELECT;
+
currentCoreResults << column;
// In this case we end it here.
@@ -444,6 +449,21 @@ void SelectResolver::resolveDbAndTable(SqliteSelect::Core::ResultColumn *resCol)
SelectResolver::Column SelectResolver::resolveRowIdColumn(SqliteExpr *expr)
{
+ // If the ROWID is used without table prefix, we rely on single source to be in the query.
+ // If there are more sources, there is no way to tell from which one the ROWID is taken.
+ if (expr->table.isNull())
+ {
+ QSet<Table> tableSources;
+ for (Column& column : currentCoreSourceColumns)
+ tableSources += column.getTable();
+
+ if (tableSources.size() == 1)
+ {
+ // Single source. We can tell this is correct for our ROWID.
+ return currentCoreSourceColumns.first();
+ }
+ }
+
// Looking for first source that can provide ROWID.
for (Column& column : currentCoreSourceColumns)
{
@@ -650,6 +670,7 @@ QList<SelectResolver::Column> SelectResolver::resolveTableFunctionColumns(Sqlite
column.type = Column::OTHER;
column.database = joinSrc->database;
column.originalDatabase = resolveDatabase(joinSrc->database);
+ column.flags |= FROM_TABLE_VALUED_FN;
if (!joinSrc->alias.isNull())
column.tableAlias = joinSrc->alias;
@@ -663,16 +684,40 @@ QList<SelectResolver::Column> SelectResolver::resolveTableFunctionColumns(Sqlite
QList<SelectResolver::Column> SelectResolver::resolveSingleSourceSubSelect(SqliteSelect::Core::SingleSource *joinSrc)
{
+ static_qstring(newAliasTpl, "column%1");
+ static_qstring(nextAliasTpl, "column%1:%2");
+
QList<Column> columnSources = resolveSubSelect(joinSrc->select);
applySubSelectAlias(columnSources, joinSrc->alias);
+ int colNum = 1;
+ QSet<QString> usedColumnNames;
QMutableListIterator<Column> it(columnSources);
while (it.hasNext())
{
- if (it.next().alias.isEmpty())
- continue;
+ Column& col = it.next();
+ usedColumnNames << (col.alias.isEmpty() ? col.column : col.alias).toLower();
- it.value().aliasDefinedInSubQuery = true;
+ // Columns named "true", "false" - require special treatment,
+ // as they will be renamed from subselects to columnN by SQLite query planner (#5065)
+ if (isReservedLiteral(col.alias) || (col.alias.isEmpty() && isReservedLiteral(col.column)))
+ {
+ QString newAlias = newAliasTpl.arg(colNum);
+ for (int i = 1; usedColumnNames.contains(newAlias); i++)
+ newAlias = nextAliasTpl.arg(colNum).arg(i);
+
+ if (!col.alias.isNull())
+ col.displayName = col.alias;
+ else
+ col.displayName = col.column;
+
+ col.alias = newAlias;
+ }
+
+ if (!col.alias.isEmpty())
+ col.aliasDefinedInSubQuery = true;
+
+ colNum++;
}
return columnSources;
@@ -680,7 +725,19 @@ QList<SelectResolver::Column> SelectResolver::resolveSingleSourceSubSelect(Sqlit
QList<SelectResolver::Column> SelectResolver::resolveOtherSource(SqliteSelect::Core::JoinSourceOther *otherSrc)
{
- return resolveSingleSource(otherSrc->singleSource);
+ QList<SelectResolver::Column> joinedColumns = resolveSingleSource(otherSrc->singleSource);
+ if (!otherSrc->joinConstraint || otherSrc->joinConstraint->expr)
+ return joinedColumns;
+
+ // Skip right-hand (aka "other") source column if it matches any of names listed in USING clause.
+ QSet<QString> usingColumns;
+ for (QString& colName : otherSrc->joinConstraint->columnNames)
+ usingColumns << colName.toLower();
+
+ return filter<SelectResolver::Column>(joinedColumns, [usingColumns](const SelectResolver::Column& col)
+ {
+ return !usingColumns.contains((col.alias.isNull() ? col.column : col.alias).toLower());
+ });
}
QList<SelectResolver::Column> SelectResolver::resolveSubSelect(SqliteSelect *select)
@@ -716,9 +773,15 @@ QList<SelectResolver::Column> SelectResolver::resolveSubSelect(SqliteSelect *sel
}
else
{
+ static_qstring(colTpl, "%1.%2 AS %3");
+ auto fn = [](const Column& c) {return colTpl.arg(c.table, c.column, c.alias);};
+ QStringList resolverColumns = map<Column, QString>(columnSourcesFromInternal, fn);
+ QStringList sqliteColumns = map<Column, QString>(columnSources, fn);
qCritical() << "Number of columns resolved by internal SchemaResolver is different than resolved by SQLite API:"
<< columnSourcesFromInternal.size() << "!=" << columnSources.size()
- << ", therefore table alias may be identified incorrectly (from resolver, but not by SQLite API)";
+ << ", therefore table alias may be identified incorrectly (from resolver, but not by SQLite API)"
+ << ". Columns were resolved from query:" << query << ". Colums resolved by SchemaResolver:"
+ << resolverColumns.join(", ") << ", while columns from SQLite:" << sqliteColumns.join(", ");
}
if (compound)
@@ -737,8 +800,15 @@ QList<SelectResolver::Column> SelectResolver::resolveView(SqliteSelect::Core::Si
QList<Column> results = sqliteResolveColumns(columnSqlTpl.arg(joinSrc->detokenize()));
applySubSelectAlias(results, (!joinSrc->alias.isNull() ? joinSrc->alias : joinSrc->table));
for (Column& column : results)
+ {
column.flags |= FROM_VIEW;
+ if (column.alias.isEmpty())
+ continue;
+
+ column.aliasDefinedInSubQuery = true;
+ }
+
return results;
}
@@ -753,10 +823,11 @@ QList<SelectResolver::Column> SelectResolver::sqliteResolveColumns(Db* db, const
for (const AliasedColumn& queryColumn : queryColumns)
{
if (!queryColumn.getDatabase().isNull())
- column.database = dbNameToAttach.valueByRight(queryColumn.getDatabase(), queryColumn.getDatabase(), Qt::CaseInsensitive);
+ column.originalDatabase = dbNameToAttach.valueByRight(queryColumn.getDatabase(), queryColumn.getDatabase(), Qt::CaseInsensitive);
else
- column.database = QString();
+ column.originalDatabase = QString();
+ column.database = queryColumn.getDatabase();
column.displayName = queryColumn.getAlias();
if (queryColumn.getTable().isNull())
{
diff --git a/SQLiteStudio3/coreSQLiteStudio/selectresolver.h b/SQLiteStudio3/coreSQLiteStudio/selectresolver.h
index a77ffe1..37c0bb8 100644
--- a/SQLiteStudio3/coreSQLiteStudio/selectresolver.h
+++ b/SQLiteStudio3/coreSQLiteStudio/selectresolver.h
@@ -64,7 +64,9 @@ class API_EXPORT SelectResolver
FROM_DISTINCT_SELECT = 0x04,
FROM_GROUPED_SELECT = 0x08,
FROM_CTE_SELECT = 0x10,
- FROM_VIEW = 0x20
+ FROM_VIEW = 0x20,
+ FROM_TABLE_VALUED_FN = 0x40,
+ FROM_RES_COL_SUBSELECT = 0x80, // for result columns that are in-line subselects (i.e. subselect that's not in FROM, but in result columns)
};
/**
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/collationmanager.h b/SQLiteStudio3/coreSQLiteStudio/services/collationmanager.h
index ef1f57a..02e2bda 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/collationmanager.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/collationmanager.h
@@ -14,9 +14,15 @@ class API_EXPORT CollationManager : public QObject
Q_OBJECT
public:
+ enum CollationType
+ {
+ FUNCTION_BASED = 0,
+ EXTENSION_BASED = 1
+ };
struct API_EXPORT Collation
{
QString name;
+ CollationType type;
QString lang;
QString code;
QStringList databases;
@@ -30,6 +36,7 @@ class API_EXPORT CollationManager : public QObject
virtual QList<CollationPtr> getCollationsForDatabase(const QString& dbName) const = 0;
virtual int evaluate(const QString& name, const QString& value1, const QString& value2) = 0;
virtual int evaluateDefault(const QString& value1, const QString& value2) = 0;
+ virtual CollationPtr getCollation(const QString &name) const = 0;
signals:
void collationListChanged();
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/config.h b/SQLiteStudio3/coreSQLiteStudio/services/config.h
index bd001c2..2410761 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/config.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/config.h
@@ -12,7 +12,7 @@
#include <QSharedPointer>
#include <QDateTime>
-const int SQLITESTUDIO_CONFIG_VERSION = 3;
+const int SQLITESTUDIO_CONFIG_VERSION = 4;
CFG_CATEGORIES(Core,
CFG_CATEGORY(General,
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/dbmanager.h b/SQLiteStudio3/coreSQLiteStudio/services/dbmanager.h
index 2b5fa41..6336eb7 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/dbmanager.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/dbmanager.h
@@ -107,7 +107,7 @@ class API_EXPORT DbManager : public QObject
/**
* @brief Gives list of valid databases.
- * @return List of open databases.
+ * @return List of valid databases.
*/
virtual QList<Db*> getValidDbList() = 0;
@@ -124,6 +124,12 @@ class API_EXPORT DbManager : public QObject
virtual QStringList getDbNames() = 0;
/**
+ * @brief Gives list of valid database names.
+ * @return List of database names that are registered and valid (no errors) in the application.
+ */
+ virtual QStringList getValidDbNames() = 0;
+
+ /**
* @brief Gives database object by its name.
* @param name Symbolic name of the database.
* @param cs Should the \p name be compared with case sensitivity?
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.cpp b/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.cpp
index c9b272d..35d9048 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.cpp
@@ -2,7 +2,6 @@
#include "services/pluginmanager.h"
#include "plugins/exportplugin.h"
#include "services/notifymanager.h"
-#include "db/queryexecutor.h"
#include "exportworker.h"
#include <QThreadPool>
#include <QTextCodec>
@@ -194,6 +193,7 @@ ExportWorker* ExportManager::prepareExport()
ExportWorker* worker = new ExportWorker(plugin, config, output);
connect(worker, SIGNAL(finished(bool,QIODevice*)), this, SLOT(finalizeExport(bool,QIODevice*)));
+ connect(worker, SIGNAL(finishedStep(int)), this, SIGNAL(finishedStep(int)));
connect(this, SIGNAL(orderWorkerToInterrupt()), worker, SLOT(interrupt()));
return worker;
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.h b/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.h
index 64d1136..7abcc70 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/exportmanager.h
@@ -9,7 +9,6 @@
#include <QObject>
class ExportPlugin;
-class QueryExecutor;
class ExportWorker;
class QBuffer;
class CfgEntry;
@@ -220,6 +219,7 @@ class API_EXPORT ExportManager : public PluginServiceBase
void exportFinished();
void exportSuccessful();
void exportFailed();
+ void finishedStep(int step);
void storeInClipboard(const QString& str);
void storeInClipboard(const QByteArray& bytes, const QString& mimeType);
void orderWorkerToInterrupt();
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.cpp b/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.cpp
index 1cdc59f..668eb72 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.cpp
@@ -34,6 +34,16 @@ QList<CollationManager::CollationPtr> CollationManagerImpl::getAllCollations() c
return collations;
}
+CollationManager::CollationPtr CollationManagerImpl::getCollation(const QString &name) const
+{
+ if (!collationsByKey.contains(name))
+ {
+ qCritical() << "Could not find requested collation" << name << ".";
+ return nullptr;
+ }
+ return collationsByKey[name];
+}
+
QList<CollationManager::CollationPtr> CollationManagerImpl::getCollationsForDatabase(const QString& dbName) const
{
QList<CollationPtr> results;
@@ -98,6 +108,7 @@ void CollationManagerImpl::storeInConfig()
for (CollationPtr coll : collations)
{
collHash["name"] = coll->name;
+ collHash["type"] = coll->type;
collHash["lang"] = coll->lang;
collHash["code"] = coll->code;
collHash["allDatabases"] = coll->allDatabases;
@@ -119,6 +130,10 @@ void CollationManagerImpl::loadFromConfig()
collHash = var.toHash();
coll = CollationPtr::create();
coll->name = collHash["name"].toString();
+ if (collHash.contains("type") && collHash["type"].toInt() == CollationType::EXTENSION_BASED)
+ coll->type = CollationType::EXTENSION_BASED;
+ else
+ coll->type = CollationType::FUNCTION_BASED;
coll->lang = updateScriptingQtLang(collHash["lang"].toString());
coll->code = collHash["code"].toString();
coll->databases = collHash["databases"].toStringList();
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.h b/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.h
index 27adffb..5ce47c6 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/collationmanagerimpl.h
@@ -17,6 +17,7 @@ class API_EXPORT CollationManagerImpl : public CollationManager
QList<CollationPtr> getCollationsForDatabase(const QString& dbName) const;
int evaluate(const QString& name, const QString& value1, const QString& value2);
int evaluateDefault(const QString& value1, const QString& value2);
+ CollationPtr getCollation(const QString &name) const;
private:
void init();
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.cpp b/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.cpp
index a7f8d2b..bcd6df8 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.cpp
@@ -478,6 +478,7 @@ QVariant ConfigImpl::getPopulateHistory(const QString& pluginName) const
void ConfigImpl::addDdlHistory(const QString& queries, const QString& dbName, const QString& dbFile)
{
+ ddlHistoryMutex.lock();
QtConcurrent::run(this, &ConfigImpl::asyncAddDdlHistory, queries, dbName, dbFile);
}
@@ -1030,6 +1031,7 @@ void ConfigImpl::asyncAddDdlHistory(const QString& queries, const QString& dbNam
}
}
db->commit();
+ ddlHistoryMutex.unlock();
emit ddlHistoryRefreshNeeded();
}
@@ -1122,12 +1124,19 @@ void ConfigImpl::updateConfigDb()
// 1->2
db->exec("UPDATE settings SET [key] = 'DataUncommittedError' WHERE [key] = 'DataUncommitedError'");
db->exec("UPDATE settings SET [key] = 'DataUncommitted' WHERE [key] = 'DataUncommited'");
- __attribute__((__fallthrough__));
+ [[fallthrough]];
}
case 2:
{
// 2->3
db->exec("ALTER TABLE groups ADD db_expanded INTEGER DEFAULT 0");
+ [[fallthrough]];
+ }
+ case 3:
+ {
+ // 3->4
+ db->exec("DELETE FROM settings WHERE [group] = 'DialogDimensions'"); // #5161
+ //[[fallthrough]];
}
// Add cases here for next versions,
// without a "break" instruction,
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.h b/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.h
index 9f0f36e..14d42e0 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/configimpl.h
@@ -154,6 +154,7 @@ class API_EXPORT ConfigImpl : public Config
SqlHistoryModel* sqlHistoryModel = nullptr;
DdlHistoryModel* ddlHistoryModel = nullptr;
QMutex sqlHistoryMutex;
+ QMutex ddlHistoryMutex;
QString sqlite3Version;
public slots:
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.cpp b/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.cpp
index 6258f71..46c8178 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.cpp
@@ -247,6 +247,18 @@ QStringList DbManagerImpl::getDbNames()
return nameToDb.keys();
}
+QStringList DbManagerImpl::getValidDbNames()
+{
+ QReadLocker lock(&listLock);
+ QStringList result;
+ for (Db* db : dbList)
+ {
+ if (db->isValid())
+ result << db->getName();
+ }
+ return result;
+}
+
Db* DbManagerImpl::getByName(const QString &name, Qt::CaseSensitivity cs)
{
QReadLocker lock(&listLock);
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.h b/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.h
index 5f99f86..867dd92 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/dbmanagerimpl.h
@@ -40,6 +40,7 @@ class API_EXPORT DbManagerImpl : public DbManager
QList<Db*> getValidDbList();
QList<Db*> getConnectedDbList();
QStringList getDbNames();
+ QStringList getValidDbNames();
Db* getByName(const QString& name, Qt::CaseSensitivity cs = Qt::CaseInsensitive);
Db* getByPath(const QString& path);
Db* createInMemDb(bool pureInit = false);
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/impl/functionmanagerimpl.cpp b/SQLiteStudio3/coreSQLiteStudio/services/impl/functionmanagerimpl.cpp
index 1b49f3b..ef0fbc9 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/impl/functionmanagerimpl.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/impl/functionmanagerimpl.cpp
@@ -721,35 +721,40 @@ QVariant FunctionManagerImpl::nativeImport(const QList<QVariant> &args, Db *db,
ImportManager::StandardImportConfig stdConfig;
stdConfig.inputFileName = args[0].toString();
stdConfig.ignoreErrors = true;
- stdConfig.skipTransaction = true;
+ stdConfig.noDbLock = true;
if (args.size() > 3)
stdConfig.codec = args[3].toString();
if (args.size() > 4)
{
// Parsing plugin options
- int idx;
- QString option;
- QString value;
- CfgEntry* cfg;
QStringList lines = args[4].toString().split(QRegExp("[\r\n]+"));
for (const QString& line : lines)
{
- idx = line.indexOf("=");
+ int idx = line.indexOf("=");
if (idx == -1)
{
qDebug() << "Invalid options entry for import() function call:" << line;
continue;
}
- option = line.left(idx).trimmed();
- cfg = CfgMain::getEntryByPath(option);
+ QString option = line.left(idx).trimmed();
+ CfgEntry* cfg = CfgMain::getEntryByPath(option);
if (!cfg)
{
qDebug() << "Invalid option name for import() function call:" << option;
continue;
}
- value = line.mid(idx + 1);
- cfg->set(value);
+
+ QVariant varValue = line.mid(idx + 1);
+ QVariant defValue = cfg->getDefaultValue();
+ QVariant::Type expectedType = defValue.type();
+ if (varValue.type() != expectedType && !varValue.convert(expectedType))
+ {
+ qDebug() << "Invalid option value for import() function call:" << option << ", invalid value was:" << varValue.toString()
+ << ", expected value type was:" << defValue.typeName() << ", but given value could not be converted to that type.";
+ continue;
+ }
+ cfg->set(varValue);
}
}
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/importmanager.cpp b/SQLiteStudio3/coreSQLiteStudio/services/importmanager.cpp
index a06a743..7b38211 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/importmanager.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/services/importmanager.cpp
@@ -74,7 +74,10 @@ void ImportManager::importToTable(Db* db, const QString& table, bool async)
if (async)
QThreadPool::globalInstance()->start(worker);
else
+ {
worker->run();
+ delete worker;
+ }
}
void ImportManager::interrupt()
diff --git a/SQLiteStudio3/coreSQLiteStudio/services/importmanager.h b/SQLiteStudio3/coreSQLiteStudio/services/importmanager.h
index 9e9b160..c812ee8 100644
--- a/SQLiteStudio3/coreSQLiteStudio/services/importmanager.h
+++ b/SQLiteStudio3/coreSQLiteStudio/services/importmanager.h
@@ -39,6 +39,7 @@ class API_EXPORT ImportManager : public PluginServiceBase
bool ignoreErrors = false;
bool skipTransaction = false;
+ bool noDbLock = false;
};
enum StandardConfigFlag
diff --git a/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.cpp b/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.cpp
index 819d222..b2f46e5 100644
--- a/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.cpp
@@ -26,17 +26,22 @@ void SqlFileExecutor::execSqlFromFile(Db* db, const QString& filePath, bool igno
return;
}
- fkWasEnabled = db->exec("PRAGMA foreign_keys")->getSingleCell().toBool();
- if (fkWasEnabled)
- {
- SqlQueryPtr res = db->exec("PRAGMA foreign_keys = 0");
- if (res->isError())
- {
- qDebug() << "Failed to temporarily disable foreign keys enforcement:" << db->getErrorText();
- emit execEnded();
- return;
- }
- }
+ // #4871 is caused by this. On one hand it doesn't make sense to disable FK for script execution
+ // (after all we're trying to execute script just like from SQL Editor, but we do it directly from file),
+ // but on the other hand, it was introduced probably for some reason. It's kept commented for now to see
+ // if good reason for it reappears. It's a subject for removal in future (until end of 2025).
+ //
+ // fkWasEnabled = db->exec("PRAGMA foreign_keys")->getSingleCell().toBool();
+ // if (fkWasEnabled)
+ // {
+ // SqlQueryPtr res = db->exec("PRAGMA foreign_keys = 0");
+ // if (res->isError())
+ // {
+ // qDebug() << "Failed to temporarily disable foreign keys enforcement:" << db->getErrorText();
+ // emit execEnded();
+ // return;
+ // }
+ // }
// Exec file
executionInProgress = 1;
@@ -113,12 +118,14 @@ void SqlFileExecutor::execInThread()
QList<QPair<QString, QString>> errors = executeFromStream(stream, executed, attemptedExecutions, ok, fileSize);
int millis = timer.elapsed();
- if (fkWasEnabled)
- {
- SqlQueryPtr res = db->exec("PRAGMA foreign_keys = 1");
- if (res->isError())
- qDebug() << "Failed to restore foreign keys enforcement after execution SQL from file:" << res->getErrorText();
- }
+ // See comment about fkWasEnabled above.
+ //
+ // if (fkWasEnabled)
+ // {
+ // SqlQueryPtr res = db->exec("PRAGMA foreign_keys = 1");
+ // if (res->isError())
+ // qDebug() << "Failed to restore foreign keys enforcement after execution SQL from file:" << res->getErrorText();
+ // }
if (executionInProgress.loadAcquire())
{
@@ -215,7 +222,7 @@ bool SqlFileExecutor::shouldSkipQuery(const QString& sql)
if (sql.trimmed().isEmpty() || !db->isComplete(sql))
return true;
- QString upper = sql.toUpper().trimmed().split("\n").last().trimmed();
+ QString upper = sql.toUpper().trimmed();
return (upper.startsWith("BEGIN") ||
upper.startsWith("COMMIT") ||
upper.startsWith("ROLLBACK") ||
diff --git a/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.h b/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.h
index fbca301..0d03b04 100644
--- a/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.h
+++ b/SQLiteStudio3/coreSQLiteStudio/sqlfileexecutor.h
@@ -25,7 +25,7 @@ class API_EXPORT SqlFileExecutor : public QObject
QAtomicInt executionInProgress = 0;
Db* db = nullptr;
- bool fkWasEnabled = true;
+ //bool fkWasEnabled = true; // See comment about fkWasEnabled in cpp file.
bool ignoreErrors = false;
QString codec;
QString filePath;
diff --git a/SQLiteStudio3/coreSQLiteStudio/sqlitestudio.cpp b/SQLiteStudio3/coreSQLiteStudio/sqlitestudio.cpp
index 4e966fd..94daad3 100644
--- a/SQLiteStudio3/coreSQLiteStudio/sqlitestudio.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/sqlitestudio.cpp
@@ -42,7 +42,7 @@
DEFINE_SINGLETON(SQLiteStudio)
-static const int sqlitestudioVersion = 30404;
+static const int sqlitestudioVersion = 30413;
SQLiteStudio::SQLiteStudio()
{
diff --git a/SQLiteStudio3/coreSQLiteStudio/tablemodifier.cpp b/SQLiteStudio3/coreSQLiteStudio/tablemodifier.cpp
index 1a8abb6..c449a31 100644
--- a/SQLiteStudio3/coreSQLiteStudio/tablemodifier.cpp
+++ b/SQLiteStudio3/coreSQLiteStudio/tablemodifier.cpp
@@ -68,13 +68,53 @@ void TableModifier::renameTo(const QString& newName, bool doCopyData)
if (!createTable)
return;
- // Using ALTER TABLE RENAME TO is not a good solution here, because it automatically renames all occurrences in REFERENCES,
+ // Firstly, using ALTER TABLE RENAME TO is not a good solution here, because it automatically renames all occurrences in REFERENCES,
// which we don't want, because we rename a lot to temporary tables and drop them.
- sqls << QString("CREATE TABLE %1 AS SELECT * FROM %2%3;").arg(wrapObjIfNeeded(newName), wrapObjIfNeeded(table), doCopyData ? "" : " LIMIT 0")
- << QString("DROP TABLE %1;").arg(wrapObjIfNeeded(table));
+ //
+ // Secondly, we need to identify if a table has column with "reserved literal" used as column name - i.e. "true" or "false".
+ // This is allowed by SQLite, but it's treated strangely by SQLite. In many cases result column of such name is renamed to columnN.
+ // Example of such case when reserved literal column is used in source table of CREATE TABLE trg AS SELECT * FROM src;
+ // It was identified during investigation of #5065.
+
+ bool hasReservedColName = false;
+ for (SqliteCreateTable::Column* column : createTable->columns)
+ {
+ if (isReservedLiteral(column->name))
+ {
+ hasReservedColName = true;
+ break;
+ }
+ }
+
+ if (hasReservedColName)
+ {
+ SqliteCreateTable* ctCopy = createTable->typeClone<SqliteCreateTable>();
+ ctCopy->table = newName;
+ ctCopy->rebuildTokens();
+ sqls << ctCopy->detokenize();
+
+ if (doCopyData)
+ {
+ QStringList colList;
+ for (SqliteCreateTable::Column* column : createTable->columns)
+ colList << wrapObjIfNeeded(column->name);
+
+ QString cols = colList.join(", ");
+ sqls << QString("INSERT INTO %1 (%2) SELECT %2 FROM %3").arg(wrapObjIfNeeded(newName), cols, wrapObjIfNeeded(table));
+ }
+
+ sqls << QString("DROP TABLE %1;").arg(wrapObjIfNeeded(table));
+ delete ctCopy;
+ }
+ else
+ {
+ // No reserved literal as columns. We can use simple way.
+ sqls << QString("CREATE TABLE %1 AS SELECT * FROM %2%3;").arg(wrapObjIfNeeded(newName), wrapObjIfNeeded(table), doCopyData ? "" : " LIMIT 0")
+ << QString("DROP TABLE %1;").arg(wrapObjIfNeeded(table));
+ }
- table = newName;
createTable->table = newName;
+ table = newName;
}
QString TableModifier::renameToTemp(bool doCopyData)
@@ -132,7 +172,7 @@ void TableModifier::handleFks()
subModifier.tableColMap = tableColMap; // for identifying renamed columns
subModifier.newName = fkTable;
subModifier.tablesHandledForFk = tablesHandledForFk;
- subModifier.handleFks(originalTable, newName);
+ subModifier.handleFkAsSubModifier(originalTable, newName);
sqls += subModifier.generateSqls();
modifiedTables << fkTable;
@@ -150,7 +190,7 @@ void TableModifier::handleFks()
}
}
-void TableModifier::handleFks(const QString& oldName, const QString& theNewName)
+void TableModifier::handleFkAsSubModifier(const QString& oldName, const QString& theNewName)
{
if (!handleFkConstrains(createTable.data(), oldName, theNewName))
return;
@@ -171,7 +211,7 @@ void TableModifier::handleFks(const QString& oldName, const QString& theNewName)
simpleHandleTriggers();
}
-bool TableModifier::handleFks(SqliteForeignKey* fk, const QString& oldName, const QString& theNewName)
+bool TableModifier::handleFkStmt(SqliteForeignKey* fk, const QString& oldName, const QString& theNewName)
{
// If table was not renamed (but uses temp table name), we will rename temp name into target name.
// If table was renamed, we will rename old name to new name.
@@ -193,7 +233,7 @@ bool TableModifier::handleFkConstrains(SqliteCreateTable* stmt, const QString& o
bool modified = false;
for (SqliteCreateTable::Constraint*& fk : stmt->getForeignKeysByTable(oldName))
{
- if (handleFks(fk->foreignKey, oldName, theNewName))
+ if (handleFkStmt(fk->foreignKey, oldName, theNewName))
{
modified = true;
if (fk->foreignKey->indexedColumns.isEmpty())
@@ -206,7 +246,7 @@ bool TableModifier::handleFkConstrains(SqliteCreateTable* stmt, const QString& o
for (SqliteCreateTable::Column::Constraint*& fk : stmt->getColumnForeignKeysByTable(oldName))
{
- if (handleFks(fk->foreignKey, oldName, theNewName))
+ if (handleFkStmt(fk->foreignKey, oldName, theNewName))
{
modified = true;
if (fk->foreignKey->indexedColumns.isEmpty())
@@ -929,23 +969,14 @@ void TableModifier::simpleHandleIndexes()
{
SchemaResolver resolver(db);
resolver.setIgnoreSystemObjects(true);
- QList<SqliteCreateIndexPtr> parsedIndexesForTable = resolver.getParsedIndexesForTable(originalTable);
- for (SqliteCreateIndexPtr& index : parsedIndexesForTable)
- sqls << index->detokenize();
+ sqls += resolver.getIndexDdlsForTable(originalTable);
}
void TableModifier::simpleHandleTriggers(const QString& view)
{
SchemaResolver resolver(db);
resolver.setIgnoreSystemObjects(true);
- QList<SqliteCreateTriggerPtr> parsedTriggers ;
- if (!view.isNull())
- parsedTriggers = resolver.getParsedTriggersForView(view);
- else
- parsedTriggers = resolver.getParsedTriggersForTable(originalTable);
-
- for (SqliteCreateTriggerPtr& trig : parsedTriggers)
- sqls << trig->detokenize();
+ sqls += resolver.getTriggerDdlsForTableOrView(view.isNull() ? originalTable : view);
}
SqliteQueryPtr TableModifier::parseQuery(const QString& ddl)
diff --git a/SQLiteStudio3/coreSQLiteStudio/tablemodifier.h b/SQLiteStudio3/coreSQLiteStudio/tablemodifier.h
index 600a761..0e5b383 100644
--- a/SQLiteStudio3/coreSQLiteStudio/tablemodifier.h
+++ b/SQLiteStudio3/coreSQLiteStudio/tablemodifier.h
@@ -70,8 +70,8 @@ class API_EXPORT TableModifier
* Finds all tables referencing currently modified table and updates their referenced table name and columns.
*/
void handleFks();
- void handleFks(const QString& oldName, const QString& theNewName);
- bool handleFks(SqliteForeignKey* fk, const QString& oldName, const QString& theNewName);
+ void handleFkAsSubModifier(const QString& oldName, const QString& theNewName);
+ bool handleFkStmt(SqliteForeignKey* fk, const QString& oldName, const QString& theNewName);
bool handleFkConstrains(SqliteCreateTable* stmt, const QString& oldName, const QString& theNewName);
bool handleName(const QString& oldName, QString& valueToUpdate);
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.cpp b/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.cpp
new file mode 100644
index 0000000..ad283ca
--- /dev/null
+++ b/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.cpp
@@ -0,0 +1,59 @@
+#include "dialogsizehandler.h"
+#include "services/config.h"
+#include <QEvent>
+#include <QTimer>
+#include <QWidget>
+#include <QScreen>
+#include <QGuiApplication>
+
+DialogSizeHandler::DialogSizeHandler(QObject *parent) :
+ DialogSizeHandler(parent->objectName(), parent)
+{
+}
+
+DialogSizeHandler::DialogSizeHandler(const QString &key, QObject *parent) :
+ QObject(parent), configKey(key)
+{
+ saveTimer = new QTimer(this);
+ saveTimer->setInterval(500);
+ saveTimer->setSingleShot(true);
+ connect(saveTimer, SIGNAL(timeout()), this, SLOT(doSave()));
+
+ QRect geom = CFG->get(CONFIG_GROUP, configKey).toRect();
+ if (geom.isValid() && qApp->primaryScreen()->geometry().contains(geom))
+ {
+ QWidget* w = qobject_cast<QWidget*>(parent);
+ w->setGeometry(geom);
+ }
+}
+
+DialogSizeHandler::~DialogSizeHandler()
+{
+}
+
+void DialogSizeHandler::applyFor(QObject *parent)
+{
+ applyFor(parent->objectName(), parent);
+}
+
+void DialogSizeHandler::applyFor(const QString &key, QObject *parent)
+{
+ DialogSizeHandler* handler = new DialogSizeHandler(key, parent);
+ parent->installEventFilter(handler);
+}
+
+bool DialogSizeHandler::eventFilter(QObject *obj, QEvent *event)
+{
+ if (event->type() == QEvent::Resize || event->type() == QEvent::Move)
+ {
+ QWidget* w = qobject_cast<QWidget*>(obj);
+ recentGeometry = w->geometry();
+ saveTimer->start();
+ }
+ return false;
+}
+
+void DialogSizeHandler::doSave()
+{
+ CFG->set(CONFIG_GROUP, configKey, recentGeometry);
+}
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.h b/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.h
new file mode 100644
index 0000000..916f65d
--- /dev/null
+++ b/SQLiteStudio3/guiSQLiteStudio/common/dialogsizehandler.h
@@ -0,0 +1,34 @@
+#ifndef DIALOGSIZEHANDLER_H
+#define DIALOGSIZEHANDLER_H
+
+#include <QObject>
+#include <QRect>
+
+class QTimer;
+
+class DialogSizeHandler : public QObject
+{
+ Q_OBJECT
+public:
+ explicit DialogSizeHandler(QObject *parent);
+ DialogSizeHandler(const QString& key, QObject *parent);
+ virtual ~DialogSizeHandler();
+
+ static void applyFor(QObject *parent);
+ static void applyFor(const QString& key, QObject *parent);
+
+protected:
+ bool eventFilter(QObject *obj, QEvent *event) override;
+
+private:
+ static const constexpr char* CONFIG_GROUP = "DialogDimensions";
+
+ QString configKey;
+ QTimer* saveTimer = nullptr;
+ QRect recentGeometry;
+
+public slots:
+ void doSave();
+};
+
+#endif // DIALOGSIZEHANDLER_H
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.cpp b/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.cpp
index 168c7f9..7866888 100644
--- a/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.cpp
@@ -142,7 +142,13 @@ void WidgetCover::hide()
void WidgetCover::setProgress(int value)
{
- busyBar->setValue(value);
+ if (undetermined)
+ {
+ busyBar->setRange(0, value);
+ busyBar->setValue(value);
+ }
+ else
+ busyBar->setValue(value);
}
QEasingCurve WidgetCover::getEasingCurve() const
@@ -203,6 +209,7 @@ void WidgetCover::displayProgress(int maxValue, const QString& format)
return;
busyBar->setRange(0, maxValue);
+ undetermined = maxValue == 0;
if (!format.isNull())
busyBar->setFormat(format);
@@ -224,6 +231,7 @@ void WidgetCover::initWithProgressBarOnly(const QString& format)
busyBar->setRange(0, 100);
busyBar->setFormat(format);
busyBar->setTextVisible(true);
+ undetermined = false;
containerLayout->addWidget(busyBar, 0, 0);
}
@@ -236,6 +244,7 @@ void WidgetCover::initWithInterruptContainer(const QString& interruptButtonText)
busyBar = new QProgressBar();
busyBar->setRange(0, 0);
busyBar->setTextVisible(false);
+ undetermined = true;
containerLayout->addWidget(busyBar, 0, 0);
containerLayout->addWidget(cancelButton, 1, 0);
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.h b/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.h
index 0b7a2f5..3d64ef5 100644
--- a/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.h
+++ b/SQLiteStudio3/guiSQLiteStudio/common/widgetcover.h
@@ -55,6 +55,7 @@ class GUI_API_EXPORT WidgetCover : public QWidget
QGridLayout* containerLayout = nullptr;
QPushButton* cancelButton = nullptr;
QProgressBar* busyBar = nullptr;
+ bool undetermined = false;
signals:
void cancelClicked();
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.cpp b/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.cpp
index b5b0264..a81508d 100644
--- a/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.cpp
@@ -157,6 +157,11 @@ void WidgetStateIndicator::setVisible(bool visible, const QString& msg)
hide();
}
+bool WidgetStateIndicator::isVisible() const
+{
+ return labelParent->isVisible();
+}
+
void WidgetStateIndicator::release()
{
setVisible(false);
diff --git a/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.h b/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.h
index 28c6e0b..065c87a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.h
+++ b/SQLiteStudio3/guiSQLiteStudio/common/widgetstateindicator.h
@@ -34,6 +34,7 @@ class GUI_API_EXPORT WidgetStateIndicator : public QObject
void show(const QString& msg = QString());
void hide();
void setVisible(bool visible, const QString& msg = QString());
+ bool isVisible() const;
void release();
void info(const QString& msg);
void warn(const QString& msg);
diff --git a/SQLiteStudio3/guiSQLiteStudio/completer/completerwindow.cpp b/SQLiteStudio3/guiSQLiteStudio/completer/completerwindow.cpp
index 68ca58d..fb5dac9 100644
--- a/SQLiteStudio3/guiSQLiteStudio/completer/completerwindow.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/completer/completerwindow.cpp
@@ -236,9 +236,9 @@ QString CompleterWindow::getStatusMsg(const QModelIndex& index)
case ExpectedToken::OPERATOR:
return tr("Operator: %1", "completer statusbar").arg(value);
case ExpectedToken::STRING:
- return tr("String", "completer statusbar");
+ return tr("String", "completer statusbar").arg(value);
case ExpectedToken::NUMBER:
- return tr("Number", "completer statusbar").arg(value);
+ return tr("Number", "completer statusbar");
case ExpectedToken::BLOB:
return tr("Binary data", "completer statusbar").arg(value);
case ExpectedToken::COLLATION:
diff --git a/SQLiteStudio3/guiSQLiteStudio/configmapper.cpp b/SQLiteStudio3/guiSQLiteStudio/configmapper.cpp
index 704104b..ea176ad 100644
--- a/SQLiteStudio3/guiSQLiteStudio/configmapper.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/configmapper.cpp
@@ -441,7 +441,6 @@ void ConfigMapper::saveFromWidget(QWidget* widget, CfgEntry* cfgEntry)
saveCommonConfigFromWidget(widget, cfgEntry);
}
-
bool ConfigMapper::saveCustomConfigFromWidget(QWidget* widget, CfgEntry* key)
{
QList<CustomConfigWidgetPlugin*> handlers;
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/columncollatepanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/columncollatepanel.cpp
index de78b2b..d10dc5a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/columncollatepanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/columncollatepanel.cpp
@@ -102,6 +102,8 @@ void ColumnCollatePanel::storeConfiguration()
if (ui->namedCheck->isChecked())
constr->name = ui->namedEdit->text();
+ else
+ constr->name.clear();
constr->collationName = ui->collationCombo->currentText();
}
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/columndefaultpanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/columndefaultpanel.cpp
index bb70c81..79b6b6a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/columndefaultpanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/columndefaultpanel.cpp
@@ -139,6 +139,8 @@ void ColumnDefaultPanel::storeConfiguration()
if (ui->namedCheck->isChecked())
constr->name = ui->namedEdit->text();
+ else
+ constr->name.clear();
}
void ColumnDefaultPanel::storeExpr(SqliteCreateTable::Column::Constraint* constr)
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/columngeneratedpanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/columngeneratedpanel.cpp
index 308b868..8e49c93 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/columngeneratedpanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/columngeneratedpanel.cpp
@@ -133,6 +133,8 @@ void ColumnGeneratedPanel::storeConfiguration()
if (ui->namedCheck->isChecked())
constr->name = ui->namedEdit->text();
+ else
+ constr->name.clear();
}
void ColumnGeneratedPanel::storeExpr(SqliteCreateTable::Column::Constraint* constr)
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/columnprimarykeypanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/columnprimarykeypanel.cpp
index fa7b7c3..2c70eb9 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/columnprimarykeypanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/columnprimarykeypanel.cpp
@@ -61,7 +61,7 @@ void ColumnPrimaryKeyPanel::readConstraint()
if (!constr->name.isNull())
{
- ui->namedCheck->setEnabled(true);
+ ui->namedCheck->setChecked(true);
ui->namedEdit->setText(constr->name);
}
@@ -122,6 +122,8 @@ void ColumnPrimaryKeyPanel::storeConfiguration()
if (ui->namedCheck->isChecked())
constr->name = ui->namedEdit->text();
+ else
+ constr->name.clear();
if (ui->conflictCheck->isChecked() && ui->conflictCombo->currentIndex() > -1)
constr->onConflict = sqliteConflictAlgo(ui->conflictCombo->currentText());
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/columnuniqueandnotnullpanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/columnuniqueandnotnullpanel.cpp
index 7c0f5a8..3b455e9 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/columnuniqueandnotnullpanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/columnuniqueandnotnullpanel.cpp
@@ -93,6 +93,8 @@ void ColumnUniqueAndNotNullPanel::storeConfiguration()
SqliteCreateTable::Column::Constraint* constr = dynamic_cast<SqliteCreateTable::Column::Constraint*>(constraint.data());
if (ui->namedCheck->isChecked())
constr->name = ui->namedEdit->text();
+ else
+ constr->name.clear();
if (ui->conflictCheck->isChecked() && ui->conflictCombo->currentIndex() > -1)
constr->onConflict = sqliteConflictAlgo(ui->conflictCombo->currentText());
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.cpp
index 4f3e350..3296532 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.cpp
@@ -29,6 +29,16 @@ void ConstraintPanel::setConstraint(SqliteStatement* stmt)
constraintAvailable();
}
+void ConstraintPanel::setCreateTableStmt(SqliteCreateTable *stmt)
+{
+ createTableStmt = stmt;
+}
+
+void ConstraintPanel::setColumnStmt(SqliteCreateTable::Column *stmt)
+{
+ columnStmt = stmt;
+}
+
void ConstraintPanel::storeDefinition()
{
storeConfiguration();
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.h b/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.h
index 9f875a9..f7ed9d5 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/constraintpanel.h
@@ -16,6 +16,8 @@ class GUI_API_EXPORT ConstraintPanel : public QWidget
virtual ~ConstraintPanel();
void setConstraint(SqliteStatement* stmt);
+ void setCreateTableStmt(SqliteCreateTable* stmt);
+ void setColumnStmt(SqliteCreateTable::Column* stmt);
void storeDefinition();
virtual void setDb(Db* value);
@@ -68,6 +70,8 @@ class GUI_API_EXPORT ConstraintPanel : public QWidget
Db* db = nullptr;
QPointer<SqliteStatement> constraint;
+ QPointer<SqliteCreateTable> createTableStmt;
+ QPointer<SqliteCreateTable::Column> columnStmt;
public slots:
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.cpp b/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.cpp
index cecf5f4..5e85915 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.cpp
@@ -53,6 +53,8 @@ bool TableForeignKeyPanel::validate()
setValidState(combo, idxOk, tr("Pick the foreign column."));
if (!idxOk)
columnsSelected = false;
+ else
+ handleFkTypeMatched(combo, check->property(UI_PROP_COLUMN).toString(), combo->currentText());
break;
}
@@ -386,6 +388,36 @@ void TableForeignKeyPanel::storeMatchCondition(const QString& reaction)
constr->foreignKey->conditions << condition;
}
+void TableForeignKeyPanel::handleFkTypeMatched(QWidget* indicatorParent, const QString &localColumn, const QString fkColumn)
+{
+ SqliteCreateTable::Column* column = createTableStmt->getColumn(localColumn);
+ if (!column || !column->type)
+ return;
+
+ QString localType = column->type->toDataType().toString();
+
+ // FK column type
+ QString fkTable = ui->fkTableCombo->currentText();
+ if (!fkTableTypesCache.contains(fkTable, Qt::CaseInsensitive))
+ {
+ SchemaResolver resolver(db);
+ fkTableTypesCache[fkTable] = resolver.getTableColumnDataTypesByName(fkTable);
+ }
+
+ StrHash<DataType> fkTypes = fkTableTypesCache.value(fkTable, Qt::CaseInsensitive);
+ if (!fkTypes.contains(fkColumn, Qt::CaseInsensitive))
+ return;
+
+ QString fkType = fkTypes.value(fkColumn, Qt::CaseInsensitive).toString();
+
+ if (localType.toLower().trimmed() != fkType.toLower().trimmed())
+ {
+ setValidStateWarning(indicatorParent,
+ tr("Referenced column type (%1) is different than type declared for local column (%2). It may cause issues while inserting or updating data.")
+ .arg(fkType, localType));
+ }
+}
+
void TableForeignKeyPanel::readTables()
{
SchemaResolver resolver(db);
diff --git a/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.h b/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.h
index cecc04a..a6d48e6 100644
--- a/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/constraints/tableforeignkeypanel.h
@@ -4,6 +4,7 @@
#include "constraintpanel.h"
#include "parser/ast/sqlitecreatetable.h"
#include "guiSQLiteStudio_global.h"
+#include "common/strhash.h"
#include <QStringListModel>
#include <QWidget>
@@ -40,12 +41,14 @@ class GUI_API_EXPORT TableForeignKeyPanel : public ConstraintPanel
int getColumnIndex(const QString& colName);
void storeCondition(SqliteForeignKey::Condition::Action action, const QString& reaction);
void storeMatchCondition(const QString& reaction);
+ void handleFkTypeMatched(QWidget* indicatorParent, const QString& localColumn, const QString fkColumn);
Ui::TableForeignKeyPanel *ui = nullptr;
QGridLayout* columnsLayout = nullptr;
int totalColumns = 0;
QStringListModel fkColumnsModel;
QSignalMapper* columnSignalMapping = nullptr;
+ StrHash<StrHash<DataType>> fkTableTypesCache;
private slots:
void updateState();
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.cpp
index b9ca7b7..a3ba2ab 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.cpp
@@ -10,6 +10,7 @@
#include <QScreen>
#include <QLineEdit>
#include <QScrollBar>
+#include <QCompleter>
FkComboBox::FkComboBox(QWidget* parent, int dropDownViewMinWidth)
: QComboBox(parent), dropDownViewMinWidth(dropDownViewMinWidth)
@@ -45,8 +46,8 @@ QString FkComboBox::getSqlForFkEditor(Db* db, SqlQueryModelColumn* columnModel,
src = wrapObjIfNeeded(fk->foreignTable);
if (i == 0)
{
- firstSrcCol = col;
fullSrcCol = src + "." + col;
+ firstSrcCol = fullSrcCol;
selectedCols << dbColTpl.arg(fullSrcCol, wrapObjIfNeeded(columnModel->column));
}
@@ -89,7 +90,7 @@ QString FkComboBox::getSqlForFkEditor(Db* db, SqlQueryModelColumn* columnModel,
QString currValueColName = generateUniqueName("curr", usedNames);
QString currValueExpr = currentValue.isNull() ?
currNullValueTpl.arg(firstSrcCol, currValueColName) :
- currValueTpl.arg(firstSrcCol, wrapValueIfNeeded(currentValue), currValueColName);
+ currValueTpl.arg(firstSrcCol, valueToSqlLiteral(currentValue), currValueColName);
return sql.arg(
selectedCols.join(", "),
@@ -110,8 +111,6 @@ void FkComboBox::setValue(const QVariant& value)
bool doExecQuery = (sourceValue != value || comboModel->getQuery().isNull());
sourceValue = value;
setCurrentText(value.toString());
- if (!value.isNull() && isEditable())
- lineEdit()->selectAll();
if (doExecQuery)
{
@@ -221,6 +220,13 @@ void FkComboBox::init()
comboView->horizontalHeader()->setVisible(true);
comboView->setSelectionMode(QAbstractItemView::SingleSelection);
comboView->setSelectionBehavior(QAbstractItemView::SelectRows);
+
+ connect(completer(), QOverload<const QString &>::of(&QCompleter::highlighted),
+ [=](const QString &value)
+ {
+ // #5083 In case of case-sensitive mismatch, we need to sync case, so that next/prev navigation with keybord works correctly.
+ setCurrentText(value.left(currentText().length()));
+ });
}
void FkComboBox::updateComboViewGeometry(bool initial) const
@@ -244,6 +250,19 @@ void FkComboBox::updateComboViewGeometry(bool initial) const
}
}
+void FkComboBox::updateCurrentItemIndex(const QString& value)
+{
+ QModelIndex startIdx = comboModel->index(0, modelColumn());
+ QModelIndex endIdx = comboModel->index(comboModel->rowCount() - 1, modelColumn());
+ QModelIndexList idxList = comboModel->findIndexes(startIdx, endIdx, SqlQueryItem::DataRole::VALUE, value.isNull() ? currentText() : value, 1, true);
+
+ if (idxList.size() > 0)
+ {
+ setCurrentIndex(idxList.first().row());
+ view()->selectionModel()->setCurrentIndex(idxList.first(), QItemSelectionModel::SelectCurrent);
+ }
+}
+
int FkComboBox::getFkViewHeaderWidth(bool includeScrollBar) const
{
int wd = comboView->horizontalHeader()->length();
@@ -289,7 +308,9 @@ void FkComboBox::fkDataReady()
}
}
else
+ {
setEditText(beforeLoadValue);
+ }
disableValueChangeNotifications = false;
}
@@ -305,6 +326,10 @@ void FkComboBox::notifyValueModified()
return;
oldValue = currentText();
+ disableValueChangeNotifications = true;
+ updateCurrentItemIndex();
+ disableValueChangeNotifications = false;
+
emit valueModified();
}
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.h
index 8cb22a5..647bbb6 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.h
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/fkcombobox.h
@@ -35,6 +35,7 @@ class FkComboBox : public QComboBox
void init();
void updateComboViewGeometry(bool initial) const;
+ void updateCurrentItemIndex(const QString& value = QString());
int getFkViewHeaderWidth(bool includeScrollBar) const;
QString getSql() const;
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqldatasourcequerymodel.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqldatasourcequerymodel.cpp
index a1a6cee..e02e77a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqldatasourcequerymodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqldatasourcequerymodel.cpp
@@ -28,7 +28,6 @@ void SqlDataSourceQueryModel::updateTablesInUse(const QString& inUse)
void SqlDataSourceQueryModel::applyFilter(const QString& value, FilterValueProcessor valueProc)
{
-// static_qstring(sql, "SELECT * FROM %1 WHERE %2");
if (value.isEmpty())
{
resetFilter();
@@ -39,14 +38,12 @@ void SqlDataSourceQueryModel::applyFilter(const QString& value, FilterValueProce
for (SqlQueryModelColumnPtr& column : columns)
conditions << wrapObjIfNeeded(column->getAliasedName())+" "+valueProc(value);
-// setQuery(sql.arg(getDataSource(), conditions.join(" OR ")));
queryExecutor->setFilters(conditions.join(" OR "));
- executeQuery();
+ executeQuery(true);
}
void SqlDataSourceQueryModel::applyFilter(const QStringList& values, FilterValueProcessor valueProc)
{
-// static_qstring(sql, "SELECT * FROM %1 WHERE %2");
if (values.isEmpty())
{
resetFilter();
@@ -69,7 +66,6 @@ void SqlDataSourceQueryModel::applyFilter(const QStringList& values, FilterValue
conditions << wrapObjIfNeeded(columns[i]->getAliasedName())+" "+valueProc(values[i]);
}
-// setQuery(sql.arg(getDataSource(), conditions.join(" AND ")));
queryExecutor->setFilters(conditions.join(" AND "));
executeQuery();
}
@@ -139,7 +135,7 @@ void SqlDataSourceQueryModel::resetFilter()
{
// setQuery("SELECT * FROM "+getDataSource());
queryExecutor->setFilters(QString());
- executeQuery();
+ executeQuery(true);
}
QString SqlDataSourceQueryModel::getDatabasePrefix()
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.cpp
index 771e890..81fda44 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.cpp
@@ -143,8 +143,9 @@ void SqlQueryItem::setValue(const QVariant &value, bool loadedFromDb)
// - this item was already marked as uncommitted
bool modified = (
(
- newValue != origValue ||
- origValue.isNull() != newValue.isNull()
+ newValue != origValue ||
+ origValue.isNull() != newValue.isNull() ||
+ newValue.type() != origValue.type()
) &&
!loadedFromDb
) ||
@@ -331,6 +332,18 @@ QVariant SqlQueryItem::data(int role) const
if (value.isNull())
return "NULL";
+ if (value.type() == QVariant::String)
+ {
+ QString str = value.toString();
+ return str.length() > DISPLAY_LEN_LIMIT ? QVariant(str.left(DISPLAY_LEN_LIMIT) + "...") : value;
+ }
+
+ if (value.type() == QVariant::ByteArray)
+ {
+ QByteArray bytes = value.toByteArray();
+ return bytes.size() > DISPLAY_LEN_LIMIT ? QVariant(bytes.left(DISPLAY_LEN_LIMIT) + "...") : value;
+ }
+
return value;
}
case Qt::ForegroundRole:
@@ -377,3 +390,19 @@ QVariant SqlQueryItem::data(int role) const
return QStandardItem::data(role);
}
+
+void SqlQueryItem::resetInitialFocusSelection()
+{
+ QStandardItem::setData(QVariant(), DataRole::EDIT_SKIP_INITIAL_SELECT);
+
+}
+
+void SqlQueryItem::skipInitialFocusSelection()
+{
+ QStandardItem::setData(true, DataRole::EDIT_SKIP_INITIAL_SELECT);
+}
+
+bool SqlQueryItem::shoulSkipInitialFocusSelection() const
+{
+ return QStandardItem::data(DataRole::EDIT_SKIP_INITIAL_SELECT).toBool();
+}
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.h
index 0de01c1..85dcda9 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.h
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitem.h
@@ -26,7 +26,8 @@ class GUI_API_EXPORT SqlQueryItem : public QObject, public QStandardItem
DELETED = 1007,
OLD_VALUE = 1008,
JUST_INSERTED_WITHOUT_ROWID = 1009,
- COMMITTING_ERROR_MESSAGE = 1010
+ COMMITTING_ERROR_MESSAGE = 1010,
+ EDIT_SKIP_INITIAL_SELECT = 1011 // to prevent content selection initially when editing with double-click
};
};
@@ -72,12 +73,18 @@ class GUI_API_EXPORT SqlQueryItem : public QObject, public QStandardItem
void setData(const QVariant& value, int role = Qt::UserRole + 1);
QVariant data(int role = Qt::UserRole + 1) const;
+ void resetInitialFocusSelection();
+ void skipInitialFocusSelection();
+ bool shoulSkipInitialFocusSelection() const;
+
private:
QVariant adjustVariantType(const QVariant& value);
QString getToolTip() const;
void rememberOldValue();
void clearOldValue();
+ static constexpr int DISPLAY_LEN_LIMIT = 1000;
+
QMutex valueSettingLock;
};
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.cpp
index 7b01084..55f2161 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.cpp
@@ -8,6 +8,7 @@
#include "common/utils_sql.h"
#include "fkcombobox.h"
#include "schemaresolver.h"
+#include "sqlqueryitemlineedit.h"
#include <QHeaderView>
#include <QPainter>
#include <QEvent>
@@ -71,10 +72,22 @@ QWidget* SqlQueryItemDelegate::createEditor(QWidget* parent, const QStyleOptionV
return nullptr;
}
+ bool skipInitSelection = item->shoulSkipInitialFocusSelection();
if (!item->getColumn()->getFkConstraints().isEmpty())
- return getFkEditor(item, parent, model);
+ return getFkEditor(item, skipInitSelection, parent, model);
- return getEditor(item->getValue().userType(), parent);
+ return getEditor(item->getValue().userType(), skipInitSelection, parent);
+}
+
+void SqlQueryItemDelegate::destroyEditor(QWidget* editor, const QModelIndex& index) const
+{
+ QStyledItemDelegate::destroyEditor(editor, index);
+ if (!index.isValid())
+ return;
+
+ const SqlQueryModel* model = dynamic_cast<const SqlQueryModel*>(index.model());
+ SqlQueryItem* item = model->itemFromIndex(index);
+ item->resetInitialFocusSelection();
}
QString SqlQueryItemDelegate::displayText(const QVariant& value, const QLocale& locale) const
@@ -216,100 +229,16 @@ SqlQueryItem* SqlQueryItemDelegate::getItem(const QModelIndex &index) const
return queryModel->itemFromIndex(index);
}
-QWidget* SqlQueryItemDelegate::getEditor(int type, QWidget* parent) const
+QWidget* SqlQueryItemDelegate::getEditor(int type, bool shouldSkipInitialSelection, QWidget* parent) const
{
UNUSED(type);
- QLineEdit *editor = new QLineEdit(parent);
+ SqlQueryItemLineEdit *editor = new SqlQueryItemLineEdit(shouldSkipInitialSelection, parent);
editor->setMaxLength(std::numeric_limits<int>::max());
editor->setFrame(editor->style()->styleHint(QStyle::SH_ItemView_DrawDelegateFrame, 0, editor));
return editor;
}
-QString SqlQueryItemDelegate::getSqlForFkEditor(SqlQueryItem* item) const
-{
- static_qstring(sql, "SELECT %4, %1 FROM %2%3");
- static_qstring(currValueTpl, "(%1 == %2) AS %3");
- static_qstring(currNullValueTpl, "(%1 IS NULL) AS %2");
- static_qstring(dbColTpl, "%1 AS %2");
- static_qstring(conditionTpl, "%1.%2 = %3.%4");
- static_qstring(conditionPrefixTpl, " WHERE %1");
-
- QStringList selectedCols;
- QStringList fkConditionTables;
- QStringList fkConditionCols;
- QStringList srcCols;
- Db* db = item->getModel()->getDb();
- SchemaResolver resolver(db);
-
- QList<SqlQueryModelColumn::ConstraintFk*> fkList = item->getColumn()->getFkConstraints();
- int i = 0;
- QString src;
- QString fullSrcCol;
- QString col;
- QString firstSrcCol;
- QStringList usedNames;
- for (SqlQueryModelColumn::ConstraintFk*& fk : fkList)
- {
- col = wrapObjIfNeeded(fk->foreignColumn);
- src = wrapObjIfNeeded(fk->foreignTable);
- if (i == 0)
- {
- firstSrcCol = col;
- fullSrcCol = src + "." + col;
- selectedCols << dbColTpl.arg(fullSrcCol, wrapObjIfNeeded(item->getColumn()->column));
- }
-
- if (fkConditionTables.contains(src, Qt::CaseInsensitive))
- continue;
-
- srcCols = resolver.getTableColumns(src);
- for (QString& srcCol : srcCols)
- {
- if (fk->foreignColumn.compare(srcCol, Qt::CaseInsensitive) == 0)
- continue; // Exclude matching column. We don't want the same column several times.
-
- fullSrcCol = src + "." + wrapObjIfNeeded(srcCol);
- selectedCols << fullSrcCol;
- usedNames << srcCol;
- }
-
- fkConditionCols << col;
- fkConditionTables << src;
-
- i++;
- }
-
- QStringList conditions;
- QString firstSrc = fkConditionTables.first();
- QString firstCol = fkConditionCols.first();
- for (i = 1; i < fkConditionTables.size(); i++)
- {
- src = fkConditionTables[i];
- col = fkConditionCols[i];
- conditions << conditionTpl.arg(firstSrc, firstCol, src, col);
- }
-
- QString conditionsStr;
- if (!conditions.isEmpty()) {
- conditionsStr = conditionPrefixTpl.arg(conditions.join(", "));
- }
-
- // Current value column (will be 1 for row which matches current cell value)
- QVariant value = item->getValue();
- QString currValueColName = generateUniqueName("curr", usedNames);
- QString currValueExpr = value.isNull() ?
- currNullValueTpl.arg(firstSrcCol, currValueColName) :
- currValueTpl.arg(firstSrcCol, wrapValueIfNeeded(value), currValueColName);
-
- return sql.arg(
- selectedCols.join(", "),
- fkConditionTables.join(", "),
- conditionsStr,
- currValueExpr
- );
-}
-
-QWidget* SqlQueryItemDelegate::getFkEditor(SqlQueryItem* item, QWidget* parent, const SqlQueryModel* model) const
+QWidget* SqlQueryItemDelegate::getFkEditor(SqlQueryItem* item, bool shouldSkipInitialSelection, QWidget* parent, const SqlQueryModel* model) const
{
Db* db = model->getDb();
bool countingError = false;
@@ -320,7 +249,7 @@ QWidget* SqlQueryItemDelegate::getFkEditor(SqlQueryItem* item, QWidget* parent,
notifyWarn(tr("Foreign key for column %2 has more than %1 possible values. It's too much to display in drop down list. You need to edit value manually.")
.arg(FkComboBox::MAX_ROWS_FOR_FK).arg(item->getColumn()->column));
- return getEditor(item->getValue().userType(), parent);
+ return getEditor(item->getValue().userType(), item->shoulSkipInitialFocusSelection(), parent);
}
if (rowCount == 0 && countingError && model->isStructureOutOfDate())
@@ -333,5 +262,8 @@ QWidget* SqlQueryItemDelegate::getFkEditor(SqlQueryItem* item, QWidget* parent,
FkComboBox* cb = new FkComboBox(parent, dropDownViewMinWidth);
cb->init(db, item->getColumn());
cb->setValue(item->getValue());
+ if (!shouldSkipInitialSelection)
+ cb->lineEdit()->selectAll();
+
return cb;
}
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.h
index 655eae2..b703a18 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.h
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemdelegate.h
@@ -21,6 +21,7 @@ class GUI_API_EXPORT SqlQueryItemDelegate : public QStyledItemDelegate
void paint(QPainter* painter, const QStyleOptionViewItem& option, const QModelIndex& index) const;
QWidget* createEditor(QWidget* parent, const QStyleOptionViewItem& option, const QModelIndex& index) const;
+ void destroyEditor(QWidget *editor, const QModelIndex &index) const;
QString displayText(const QVariant & value, const QLocale & locale) const;
void setEditorData(QWidget * editor, const QModelIndex & index) const;
void setModelData(QWidget * editor, QAbstractItemModel * model, const QModelIndex & index) const;
@@ -39,13 +40,12 @@ class GUI_API_EXPORT SqlQueryItemDelegate : public QStyledItemDelegate
};
SqlQueryItem* getItem(const QModelIndex &index) const;
- QWidget* getEditor(int type, QWidget* parent) const;
- QWidget* getFkEditor(SqlQueryItem* item, QWidget* parent, const SqlQueryModel *model) const;
+ QWidget* getEditor(int type, bool shouldSkipInitialSelection, QWidget* parent) const;
+ QWidget* getFkEditor(SqlQueryItem* item, bool shouldSkipInitialSelection, QWidget* parent, const SqlQueryModel *model) const;
void setEditorDataForLineEdit(QLineEdit* le, const QModelIndex& index) const;
void setEditorDataForFk(QComboBox* cb, const QModelIndex& index) const;
void setModelDataForFk(FkComboBox* editor, QAbstractItemModel* model, const QModelIndex& index) const;
void setModelDataForLineEdit(QLineEdit* editor, QAbstractItemModel* model, const QModelIndex& index) const;
- QString getSqlForFkEditor(SqlQueryItem* item) const;
qlonglong getRowCountForFkEditor(Db* db, const QString& query, bool *isError) const;
int getFkViewHeaderWidth(SqlQueryView* fkView, bool includeScrollBar) const;
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.cpp
new file mode 100644
index 0000000..8f981bc
--- /dev/null
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.cpp
@@ -0,0 +1,14 @@
+#include "sqlqueryitemlineedit.h"
+
+SqlQueryItemLineEdit::SqlQueryItemLineEdit(bool shouldSkipInitialSelection, QWidget *parent)
+ : QLineEdit{parent}, shouldSkipInitialSelection(shouldSkipInitialSelection)
+{
+
+}
+
+void SqlQueryItemLineEdit::focusInEvent(QFocusEvent* e)
+{
+ QLineEdit::focusInEvent(e);
+ if (shouldSkipInitialSelection)
+ deselect();
+}
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.h
new file mode 100644
index 0000000..76a79af
--- /dev/null
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryitemlineedit.h
@@ -0,0 +1,20 @@
+#ifndef SQLQUERYITEMLINEEDIT_H
+#define SQLQUERYITEMLINEEDIT_H
+
+#include <QLineEdit>
+
+class SqlQueryItemLineEdit : public QLineEdit
+{
+ Q_OBJECT
+
+ public:
+ explicit SqlQueryItemLineEdit(bool shouldSkipInitialSelection, QWidget *parent = nullptr);
+
+ protected:
+ void focusInEvent(QFocusEvent *e);
+
+ private:
+ bool shouldSkipInitialSelection;
+};
+
+#endif // SQLQUERYITEMLINEEDIT_H
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.cpp
index 2982415..3c44603 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.cpp
@@ -81,7 +81,7 @@ void SqlQueryModel::setAsyncMode(bool enabled)
queryExecutor->setAsyncMode(enabled);
}
-void SqlQueryModel::executeQuery()
+void SqlQueryModel::executeQuery(bool enforcePage0)
{
if (queryExecutor->isExecutionInProgress())
{
@@ -91,7 +91,7 @@ void SqlQueryModel::executeQuery()
queryExecutor->setSkipRowCounting(false);
queryExecutor->setSortOrder(sortOrder);
- queryExecutor->setPage(0);
+ queryExecutor->setPage(page > -1 && !enforcePage0 ? page : 0);
queryExecutor->setForceSimpleMode(simpleExecutionMode);
reloading = false;
@@ -157,6 +157,23 @@ bool SqlQueryModel::isEmptyQuery() const
return true;
}
+void SqlQueryModel::restoreFocusedCell()
+{
+ if (!storedFocus.isValid() || getCurrentPage() != storedFocus.forPage || getRowsPerPage() != storedFocus.forRowsPerPage ||
+ queryExecutor->getFilters() != storedFocus.forFilter)
+ {
+ forgetFocusedCell();
+ return;
+ }
+
+ QModelIndex idx = index(storedFocus.row, storedFocus.column);
+ if (idx.isValid())
+ {
+ view->setCurrentIndex(idx);
+ view->scrollTo(idx, QAbstractItemView::EnsureVisible);
+ }
+}
+
void SqlQueryModel::internalExecutionStopped()
{
reloading = false;
@@ -712,6 +729,21 @@ void SqlQueryModel::detachDependencyTables()
dbListToDetach.clear();
}
+void SqlQueryModel::rememberFocusedCell()
+{
+ QModelIndex idx = getView()->currentIndex();
+ storedFocus.row = idx.row();
+ storedFocus.column = idx.column();
+ storedFocus.forPage = getCurrentPage();
+ storedFocus.forRowsPerPage = getRowsPerPage();
+ storedFocus.forFilter = queryExecutor->getFilters();
+}
+
+void SqlQueryModel::forgetFocusedCell()
+{
+ storedFocus.reset();
+}
+
QString SqlQueryModel::generateSelectQueryForItems(const QList<SqlQueryItem*>& items)
{
QHash<QString, QVariantList> values = toValuesGroupedByColumns(items);
@@ -1439,6 +1471,7 @@ void SqlQueryModel::handleExecFinished(SqlQueryPtr results)
results.clear();
detachDatabases();
}
+ restoreFocusedCell();
}
void SqlQueryModel::handleExecFailed(int code, QString errorMessage)
@@ -1622,7 +1655,11 @@ void SqlQueryModel::storeStep1NumbersFromExecution()
{
lastExecutionTime = queryExecutor->getLastExecutionTime();
page = queryExecutor->getPage();
- sortOrder = queryExecutor->getSortOrder();
+
+ QueryExecutor::SortList newSortOrder = queryExecutor->getSortOrder();
+ if (!sortOrder.isEmpty() && newSortOrder.isEmpty())
+ notifyWarn(tr("There are less columns in the new query, sort order has been reset."));
+ sortOrder = newSortOrder;
rowsAffected = queryExecutor->getRowsAffected();
if (!queryExecutor->getSkipRowCounting())
@@ -2294,3 +2331,17 @@ QString SqlQueryModel::SelectCellsQueryBuilder::getDatabase() const
{
return database;
}
+
+bool SqlQueryModel::StoredFocus::isValid()
+{
+ return row > -1 && column > -1;
+}
+
+void SqlQueryModel::StoredFocus::reset()
+{
+ row = -1;
+ column = -1;
+ forFilter.clear();
+ forRowsPerPage = -1;
+ forPage = -1;
+}
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.h
index 43222f1..7fb6938 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodel.h
@@ -65,6 +65,8 @@ class GUI_API_EXPORT SqlQueryModel : public QStandardItemModel
bool isExecutionInProgress() const;
StrHash<QString> attachDependencyTables();
void detachDependencyTables();
+ void rememberFocusedCell();
+ void forgetFocusedCell();
/**
* @brief Disables or re-enables async query execution
@@ -244,6 +246,18 @@ class GUI_API_EXPORT SqlQueryModel : public QStandardItemModel
int argSquence = 0;
};
+ struct StoredFocus
+ {
+ int row = -1;
+ int column = -1;
+ int forPage = -1;
+ int forRowsPerPage = -1;
+ QString forFilter;
+
+ bool isValid();
+ void reset();
+ };
+
/**
* @brief commitAddedRow Inserts new row to a table.
* @param itemsInRow All cells for the new row.
@@ -316,6 +330,7 @@ class GUI_API_EXPORT SqlQueryModel : public QStandardItemModel
QueryExecutor* queryExecutor = nullptr;
Db* db = nullptr;
QList<SqlQueryModelColumnPtr> columns;
+ StoredFocus storedFocus;
/**
* @brief tablesInUse
@@ -385,6 +400,7 @@ class GUI_API_EXPORT SqlQueryModel : public QStandardItemModel
void notifyItemEditionEnded(const QModelIndex& idx);
int getRowsPerPage() const;
bool isEmptyQuery() const;
+ void restoreFocusedCell();
QString query;
QHash<QString, QVariant> queryParams;
@@ -522,7 +538,7 @@ class GUI_API_EXPORT SqlQueryModel : public QStandardItemModel
void prevPage();
void nextPage();
void lastPage();
- void executeQuery();
+ void executeQuery(bool enforcePage0 = false);
void interrupt();
void commit();
void rollback();
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.cpp
index 68287bd..cd53773 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.cpp
@@ -58,6 +58,8 @@ SqlQueryModelColumn::EditionForbiddenReason SqlQueryModelColumn::convert(QueryEx
return EditionForbiddenReason::COMMON_TABLE_EXPRESSION;
case QueryExecutor::ColumnEditionForbiddenReason::VIEW_NOT_EXPANDED:
return EditionForbiddenReason::VIEW_NOT_EXPANDED;
+ case QueryExecutor::ColumnEditionForbiddenReason::RES_INLINE_SUBSEL:
+ return EditionForbiddenReason::RESULT_INLINE_SUBSELECT;
}
return static_cast<EditionForbiddenReason>(-1);
}
@@ -66,6 +68,8 @@ QString SqlQueryModelColumn::resolveMessage(SqlQueryModelColumn::EditionForbidde
{
switch (reason)
{
+ case SqlQueryModelColumn::EditionForbiddenReason::RESULT_INLINE_SUBSELECT:
+ return QObject::tr("Cannot edit columns that are result of an inline subquery.");
case EditionForbiddenReason::COMPOUND_SELECT:
return QObject::tr("Cannot edit columns that are result of compound %1 statements (one that includes %2, %3 or %4 keywords).")
.arg("SELECT", "UNION", "INTERSECT", "EXCEPT");
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.h b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.h
index 1a347e5..042e336 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.h
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlquerymodelcolumn.h
@@ -28,6 +28,7 @@ class GUI_API_EXPORT SqlQueryModelColumn
EXPRESSION,
SMART_EXECUTION_FAILED,
DISTINCT_RESULTS,
+ RESULT_INLINE_SUBSELECT,
COMMON_TABLE_EXPRESSION,
GENERATED_COLUMN,
VIEW_NOT_EXPANDED
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryview.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryview.cpp
index d9695d7..d815654 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryview.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlqueryview.cpp
@@ -47,7 +47,6 @@ void SqlQueryView::init()
itemDelegate = new SqlQueryItemDelegate();
setItemDelegate(itemDelegate);
setMouseTracking(true);
-// setEditTriggers(QAbstractItemView::AnyKeyPressed);
setEditTriggers(QAbstractItemView::AnyKeyPressed|QAbstractItemView::EditKeyPressed);
setContextMenuPolicy(Qt::CustomContextMenu);
@@ -303,6 +302,7 @@ void SqlQueryView::itemActivated(const QModelIndex& index)
if (!editInEditorIfNecessary(item))
return;
+ item->skipInitialFocusSelection();
edit(getCurrentIndex());
}
@@ -335,7 +335,13 @@ void SqlQueryView::editCurrent()
{
QModelIndex idx = getCurrentIndex();
if (idx.isValid())
+ {
+ SqlQueryItem* item = getModel()->itemFromIndex(idx);
+ if (item)
+ item->skipInitialFocusSelection();
+
edit(idx);
+ }
}
void SqlQueryView::toggleRowsHeightAdjustment(bool enabled)
@@ -547,7 +553,7 @@ void SqlQueryView::goToReferencedRow(const QString& table, const QString& column
QString wrappedTable = wrapObjIfNeeded(table);
QString wrappedColumn = wrapObjIfNeeded(column);
- QString valueStr = wrapValueIfNeeded(value.toString());
+ QString valueStr = valueToSqlLiteral(value.toString());
EditorWindow* win = MAINWINDOW->openSqlEditor(db, sqlTpl.arg(wrappedTable, wrappedColumn, valueStr));
if (!win)
return;
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqltablemodel.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqltablemodel.cpp
index 50b0c5b..198a45f 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqltablemodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqltablemodel.cpp
@@ -355,10 +355,10 @@ void SqlTableModel::updateColumnsAndValues(const QList<SqlQueryItem*>& itemsInRo
int i = 0;
for (SqlQueryModelColumnPtr modelColumn : modelColumns)
{
+ item = itemsInRow[i++];
if (!modelColumn->canEdit())
continue;
- item = itemsInRow[i++];
if (item->getValue().isNull())
{
if (CFG_UI.General.UseDefaultValueForNull.get() && modelColumn->isDefault())
diff --git a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlviewmodel.cpp b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlviewmodel.cpp
index 1f8422c..23eac36 100644
--- a/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlviewmodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/datagrid/sqlviewmodel.cpp
@@ -20,8 +20,6 @@ void SqlViewModel::setDatabaseAndView(const QString& database, const QString& vi
this->view = view;
//setQuery("SELECT * FROM "+getDataSource());
updateTablesInUse(view);
-
- SchemaResolver resolver(db);
}
QString SqlViewModel::getDataSource()
diff --git a/SQLiteStudio3/guiSQLiteStudio/dataview.cpp b/SQLiteStudio3/guiSQLiteStudio/dataview.cpp
index e7ae9b5..8ec00d0 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dataview.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dataview.cpp
@@ -682,12 +682,6 @@ void DataView::setFormViewEnabled(bool enabled)
setTabEnabled(1, enabled);
}
-void DataView::readData()
-{
- setNavigationState(false);
- model->executeQuery();
-}
-
bool DataView::isUncommitted() const
{
return uncommittedGrid || uncommittedForm;
@@ -718,10 +712,16 @@ void DataView::totalRowsAndPagesAvailable()
updateNavigationState();
}
-void DataView::refreshData()
+void DataView::refreshData(bool keepFocus)
{
totalPagesAvailable = false;
- readData();
+ if (keepFocus)
+ model->rememberFocusedCell();
+ else
+ model->forgetFocusedCell();
+
+ setNavigationState(false);
+ model->executeQuery(!keepFocus);
}
void DataView::insertRow()
diff --git a/SQLiteStudio3/guiSQLiteStudio/dataview.h b/SQLiteStudio3/guiSQLiteStudio/dataview.h
index d8f71dc..43b6507 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dataview.h
+++ b/SQLiteStudio3/guiSQLiteStudio/dataview.h
@@ -138,7 +138,6 @@ class GUI_API_EXPORT DataView : public QTabWidget, public ExtActionContainer
void updateResultsCount(int resultsCount);
void updateCurrentFormViewRow();
void setFormViewEnabled(bool enabled);
- void readData();
void initFormViewForNewRow();
void formViewFocusFirstEditor();
void recreateFilterInputs();
@@ -179,7 +178,7 @@ class GUI_API_EXPORT DataView : public QTabWidget, public ExtActionContainer
signals:
public slots:
- void refreshData();
+ void refreshData(bool keepFocus = true);
private slots:
void dataLoadingEnded(bool successful);
diff --git a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.cpp b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.cpp
index 6514aa8..c118eb6 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.cpp
@@ -58,6 +58,11 @@ DbTreeItem* DbTreeItem::findItem(DbTreeItem::Type type, const QString& name)
return DbTreeModel::findItem(this, type, name);
}
+DbTreeItem* DbTreeItem::findFirstItem(Type type)
+{
+ return DbTreeModel::findFirstItem(this, type);
+}
+
QStandardItem* DbTreeItem::clone() const
{
return new DbTreeItem(*this);
@@ -293,6 +298,16 @@ void DbTreeItem::setIcon(const Icon& icon)
QStandardItem::setIcon(icon);
}
+bool DbTreeItem::isSchemaReady() const
+{
+ return data(DataRole::SCHEMA_READY).toBool();
+}
+
+void DbTreeItem::setSchemaReady(bool ready)
+{
+ setData(ready, DataRole::SCHEMA_READY);
+}
+
void DbTreeItem::init()
{
Type type = getType();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.h b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.h
index ba230f2..7cce7a2 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.h
+++ b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreeitem.h
@@ -38,6 +38,7 @@ class GUI_API_EXPORT DbTreeItem : public QObject, public QStandardItem
int type() const;
DbTreeItem* findItem(Type type, const QString& name);
+ DbTreeItem* findFirstItem(Type type);
QStandardItem* clone() const;
QList<QStandardItem*> childs() const;
QStringList childNames() const;
@@ -75,6 +76,8 @@ class GUI_API_EXPORT DbTreeItem : public QObject, public QStandardItem
void setHidden(bool hidden);
bool isHidden() const;
void setIcon(const Icon& icon);
+ bool isSchemaReady() const;
+ void setSchemaReady(bool ready);
private:
struct DataRole // not 'enum class' because we need autocasting to int for this one
@@ -84,7 +87,8 @@ class GUI_API_EXPORT DbTreeItem : public QObject, public QStandardItem
TYPE = 1001,
DB = 1002,
ICON_PTR = 1003,
- HIDDEN = 1004
+ HIDDEN = 1004,
+ SCHEMA_READY = 1005
};
};
diff --git a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.cpp b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.cpp
index 6620290..29bf652 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.cpp
@@ -280,7 +280,14 @@ void DbTreeModel::expanded(const QModelIndex &index)
return;
}
- if (dynamic_cast<DbTreeItem*>(item)->getType() == DbTreeItem::Type::DIR)
+ DbTreeItem* dbTreeItem = dynamic_cast<DbTreeItem*>(item);
+ if (dbTreeItem->getType() == DbTreeItem::Type::TABLE)
+ loadTableSchema(dbTreeItem);
+
+ if (dbTreeItem->getType() == DbTreeItem::Type::VIEW)
+ loadViewSchema(dbTreeItem);
+
+ if (dbTreeItem->getType() == DbTreeItem::Type::DIR)
itemFromIndex(index)->setIcon(ICONS.DIRECTORY_OPEN);
}
@@ -443,8 +450,9 @@ QString DbTreeModel::getDbToolTip(DbTreeItem* item) const
QString DbTreeModel::getTableToolTip(DbTreeItem* item) const
{
- QStringList rows;
+ const_cast<DbTreeModel*>(this)->loadTableSchema(item); // not nice to const_cast, but nothing better we can do about this
+ QStringList rows;
rows << toolTipHdrRowTmp.arg(ICONS.TABLE.getPath()).arg(tr("Table : %1", "dbtree tooltip").arg(item->text()));
QStandardItem* columnsItem = item->child(0);
@@ -499,20 +507,33 @@ void DbTreeModel::refreshSchema(Db* db, QStandardItem *item)
// Collect all db objects and build the db branch
bool sort = CFG_UI.General.SortObjects.get();
- QStringList tables = resolver.getTables();
- QStringList virtualTables;
- for (const QString& table : tables)
+ QList<SchemaResolver::TableListItem> tableListItems = resolver.getAllTableListItems();
+ QStringList tables;
+ QStringList views;
+ QSet<QString> virtualTables;
+
+ for (SchemaResolver::TableListItem& tableListItem : tableListItems)
{
- if (resolver.isVirtualTable(table))
- virtualTables << table;
+ switch (tableListItem.type)
+ {
+ case SchemaResolver::TableListItem::VIRTUAL_TABLE:
+ virtualTables << tableListItem.name;
+ [[fallthrough]];
+ case SchemaResolver::TableListItem::TABLE:
+ case SchemaResolver::TableListItem::SHADOW_TABLE:
+ tables << tableListItem.name;
+ break;
+ case SchemaResolver::TableListItem::VIEW:
+ views << tableListItem.name;
+ break;
+ case SchemaResolver::TableListItem::UNKNOWN:
+ break;
+ }
}
QList<QStandardItem*> tableItems = refreshSchemaTables(tables, virtualTables, sort);
- StrHash<QList<QStandardItem*>> allTableColumns = refreshSchemaTableColumns(resolver.getAllTableColumns());
- StrHash<QList<QStandardItem*>> indexItems = refreshSchemaIndexes(resolver.getGroupedIndexes(), sort);
- StrHash<QList<QStandardItem*>> triggerItems = refreshSchemaTriggers(resolver.getGroupedTriggers(), sort);
- QList<QStandardItem*> viewItems = refreshSchemaViews(resolver.getViews(), sort);
- refreshSchemaBuild(item, tableItems, indexItems, triggerItems, viewItems, allTableColumns);
+ QList<QStandardItem*> viewItems = refreshSchemaViews(views, sort);
+ refreshSchemaBuild(item, tableItems, viewItems);
populateChildItemsWithDb(item, db);
restoreExpandedState(expandedState, item);
}
@@ -530,7 +551,7 @@ void DbTreeModel::collectExpandedState(QHash<QString, bool> &state, QStandardIte
collectExpandedState(state, parentItem->child(i));
}
-QList<QStandardItem *> DbTreeModel::refreshSchemaTables(const QStringList &tables, const QStringList& virtualTables, bool sort)
+QList<QStandardItem *> DbTreeModel::refreshSchemaTables(const QStringList &tables, const QSet<QString>& virtualTables, bool sort)
{
QStringList sortedTables = tables;
if (sort)
@@ -548,52 +569,44 @@ QList<QStandardItem *> DbTreeModel::refreshSchemaTables(const QStringList &table
return items;
}
-StrHash<QList<QStandardItem*>> DbTreeModel::refreshSchemaTableColumns(const StrHash<QStringList> &columns)
+QList<QStandardItem*> DbTreeModel::refreshSchemaTableColumns(const QStringList& columns)
{
- QStringList sortedColumns;
bool doSort = CFG_UI.General.SortColumns.get();
- StrHash<QList<QStandardItem*>> items;
- for (const QString& key : columns.keys())
- {
- sortedColumns = columns[key];
- if (doSort)
- ::sSort(sortedColumns);
- for (const QString& column : sortedColumns)
- items[key] += DbTreeItemFactory::createColumn(column, this);
- }
+ QStringList sortedColumns = columns;
+ if (doSort)
+ ::sSort(sortedColumns);
+
+ QList<QStandardItem*> items;
+ for (const QString& column : sortedColumns)
+ items += DbTreeItemFactory::createColumn(column, this);
+
return items;
}
-StrHash<QList<QStandardItem *> > DbTreeModel::refreshSchemaIndexes(const StrHash<QStringList> &indexes, bool sort)
+QList<QStandardItem*> DbTreeModel::refreshSchemaIndexes(const QStringList& indexes, bool sort)
{
- StrHash<QList<QStandardItem *> > items;
- QStringList sortedIndexes;
- for (const QString& key : indexes.keys())
- {
- sortedIndexes = indexes[key];
- if (sort)
- sortedIndexes.sort(Qt::CaseInsensitive);
+ QStringList sortedIndexes = indexes;
+ if (sort)
+ sortedIndexes.sort(Qt::CaseInsensitive);
+
+ QList<QStandardItem*> items;
+ for (const QString& index : sortedIndexes)
+ items += DbTreeItemFactory::createIndex(index, this);
- for (const QString& index : sortedIndexes)
- items[key] += DbTreeItemFactory::createIndex(index, this);
- }
return items;
}
-StrHash<QList<QStandardItem*>> DbTreeModel::refreshSchemaTriggers(const StrHash<QStringList> &triggers, bool sort)
+QList<QStandardItem*> DbTreeModel::refreshSchemaTriggers(const QStringList& triggers, bool sort)
{
- StrHash<QList<QStandardItem*>> items;
- QStringList sortedTriggers;
- for (const QString& key : triggers.keys())
- {
- sortedTriggers = triggers[key];
- if (sort)
- sortedTriggers.sort(Qt::CaseInsensitive);
+ QStringList sortedTriggers = triggers;
+ if (sort)
+ sortedTriggers.sort(Qt::CaseInsensitive);
+
+ QList<QStandardItem*> items;
+ for (const QString& trigger : sortedTriggers)
+ items += DbTreeItemFactory::createTrigger(trigger, this);
- for (const QString& trigger : sortedTriggers)
- items[key] += DbTreeItemFactory::createTrigger(trigger, this);
- }
return items;
}
@@ -621,12 +634,68 @@ void DbTreeModel::populateChildItemsWithDb(QStandardItem *parentItem, Db* db)
}
}
+void DbTreeModel::loadTableSchema(DbTreeItem* tableItem)
+{
+ if (tableItem->isSchemaReady())
+ return;
+
+ Db* db = tableItem->getDb();
+ QString table = tableItem->text();
+
+ SchemaResolver resolver(db);
+ resolver.setIgnoreSystemObjects(!CFG_UI.General.ShowSystemObjects.get());
+
+ bool sort = CFG_UI.General.SortObjects.get();
+
+ DbTreeItem* columnsItem = tableItem->findFirstItem(DbTreeItem::Type::COLUMNS);
+ DbTreeItem* indexesItem = tableItem->findFirstItem(DbTreeItem::Type::INDEXES);
+ DbTreeItem* triggersItem = tableItem->findFirstItem(DbTreeItem::Type::TRIGGERS);
+
+ QList<QStandardItem*> tableColumns = refreshSchemaTableColumns(resolver.getTableColumns(table));
+ QList<QStandardItem*> indexItems = refreshSchemaIndexes(resolver.getIndexesForTable(table), sort);
+ QList<QStandardItem*> triggerItems = refreshSchemaTriggers(resolver.getTriggersForTable(table), sort);
+
+ for (QStandardItem* columnItem : tableColumns)
+ columnsItem->appendRow(columnItem);
+
+ for (QStandardItem* indexItem : indexItems)
+ indexesItem->appendRow(indexItem);
+
+ for (QStandardItem* triggerItem : triggerItems)
+ triggersItem->appendRow(triggerItem);
+
+ populateChildItemsWithDb(columnsItem, db);
+ populateChildItemsWithDb(indexesItem, db);
+ populateChildItemsWithDb(triggersItem, db);
+
+ tableItem->setSchemaReady(true);
+}
+
+void DbTreeModel::loadViewSchema(DbTreeItem* viewItem)
+{
+ if (viewItem->isSchemaReady())
+ return;
+
+ Db* db = viewItem->getDb();
+ QString view = viewItem->text();
+
+ SchemaResolver resolver(db);
+ resolver.setIgnoreSystemObjects(!CFG_UI.General.ShowSystemObjects.get());
+
+ bool sort = CFG_UI.General.SortObjects.get();
+
+ DbTreeItem* triggersItem = viewItem->findFirstItem(DbTreeItem::Type::TRIGGERS);
+
+ QList<QStandardItem*> triggerItems = refreshSchemaTriggers(resolver.getTriggersForView(view), sort);
+ for (QStandardItem* triggerItem : triggerItems)
+ triggersItem->appendRow(triggerItem);
+
+ viewItem->setSchemaReady(true);
+}
+
void DbTreeModel::refreshSchemaBuild(QStandardItem *dbItem,
QList<QStandardItem*> tables,
- StrHash<QList<QStandardItem*> > indexes,
- StrHash<QList<QStandardItem*> > triggers,
- QList<QStandardItem*> views,
- StrHash<QList<QStandardItem*> > allTableColumns)
+ QList<QStandardItem*> views)
{
DbTreeItem* tablesItem = DbTreeItemFactory::createTables(this);
DbTreeItem* viewsItem = DbTreeItemFactory::createViews(this);
@@ -649,14 +718,7 @@ void DbTreeModel::refreshSchemaBuild(QStandardItem *dbItem,
tableItem->appendRow(indexesItem);
tableItem->appendRow(triggersItem);
- for (QStandardItem* columnItem : allTableColumns[tableItem->text()])
- columnsItem->appendRow(columnItem);
-
- for (QStandardItem* indexItem : indexes[tableItem->text()])
- indexesItem->appendRow(indexItem);
-
- for (QStandardItem* triggerItem : triggers[tableItem->text()])
- triggersItem->appendRow(triggerItem);
+ dynamic_cast<DbTreeItem*>(tableItem)->setSchemaReady(false);
}
for (QStandardItem* viewItem : views)
{
@@ -664,8 +726,8 @@ void DbTreeModel::refreshSchemaBuild(QStandardItem *dbItem,
triggersItem = DbTreeItemFactory::createTriggers(this);
viewItem->appendRow(triggersItem);
- for (QStandardItem* triggerItem : triggers[viewItem->text()])
- triggersItem->appendRow(triggerItem);
+
+ dynamic_cast<DbTreeItem*>(viewItem)->setSchemaReady(false);
}
}
@@ -680,22 +742,6 @@ void DbTreeModel::restoreExpandedState(const QHash<QString, bool>& expandedState
restoreExpandedState(expandedState, child);
}
-DbTreeItem* DbTreeModel::findFirstItemOfType(DbTreeItem::Type type, QStandardItem* parentItem)
-{
- DbTreeItem* child = nullptr;
- for (int i = 0; i < parentItem->rowCount(); i++)
- {
- child = dynamic_cast<DbTreeItem*>(parentItem->child(i));
- if (child->getType() == type)
- return child;
-
- child = findFirstItemOfType(type, child);
- if (child)
- return child;
- }
- return nullptr;
-}
-
void DbTreeModel::dbConnected(Db* db, bool expandItem)
{
QStandardItem* item = findItem(DbTreeItem::Type::DB, db);
@@ -819,7 +865,7 @@ DbTreeItem *DbTreeModel::findItem(DbTreeItem::Type type, Db* db)
DbTreeItem* DbTreeModel::findFirstItemOfType(DbTreeItem::Type type)
{
- return findFirstItemOfType(type, root());
+ return findFirstItem(root(), type);
}
DbTreeItem *DbTreeModel::findItemBySignature(const QString &signature)
@@ -883,7 +929,7 @@ QList<DbTreeItem*> DbTreeModel::findItems(QStandardItem* parentItem, DbTreeItem:
item = dynamic_cast<DbTreeItem*>(parentItem->child(i));
// Search recursively
- if (item->getType() == DbTreeItem::Type::DIR)
+ if (item->hasChildren())
items += findItems(item, type);
if (item->getType() != type)
@@ -895,6 +941,28 @@ QList<DbTreeItem*> DbTreeModel::findItems(QStandardItem* parentItem, DbTreeItem:
return items;
}
+DbTreeItem* DbTreeModel::findFirstItem(QStandardItem* parentItem, DbTreeItem::Type type)
+{
+ for (int i = 0; i < parentItem->rowCount(); i++)
+ {
+ DbTreeItem* item = dynamic_cast<DbTreeItem*>(parentItem->child(i));
+
+ if (item->hasChildren())
+ {
+ DbTreeItem* child = findFirstItem(item, type);
+ if (child)
+ return child;
+ }
+
+ if (item->getType() != type)
+ continue;
+
+ return item;
+ }
+
+ return nullptr;
+}
+
QStandardItem* DbTreeModel::root() const
{
return invisibleRootItem();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.h b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.h
index 86dc8a6..5fb91ba 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/dbtree/dbtreemodel.h
@@ -57,6 +57,7 @@ class GUI_API_EXPORT DbTreeModel : public QStandardItemModel
static DbTreeItem* findItem(QStandardItem *parentItem, DbTreeItem::Type type, const QString &name);
static DbTreeItem* findItem(QStandardItem* parentItem, DbTreeItem::Type type, Db* db);
static QList<DbTreeItem*> findItems(QStandardItem* parentItem, DbTreeItem::Type type);
+ static DbTreeItem* findFirstItem(QStandardItem* parentItem, DbTreeItem::Type type);
static void staticInit();
static const constexpr char* MIMETYPE = "application/x-sqlitestudio-dbtreeitem";
@@ -69,16 +70,16 @@ class GUI_API_EXPORT DbTreeModel : public QStandardItemModel
void refreshSchema(Db* db, QStandardItem* item);
void collectExpandedState(QHash<QString, bool>& state, QStandardItem* parentItem = nullptr);
QStandardItem* refreshSchemaDb(Db* db);
- QList<QStandardItem*> refreshSchemaTables(const QStringList &tables, const QStringList& virtualTables, bool sort);
- StrHash<QList<QStandardItem*>> refreshSchemaTableColumns(const StrHash<QStringList>& columns);
- StrHash<QList<QStandardItem*>> refreshSchemaIndexes(const StrHash<QStringList>& indexes, bool sort);
- StrHash<QList<QStandardItem*>> refreshSchemaTriggers(const StrHash<QStringList>& triggers, bool sort);
+ QList<QStandardItem*> refreshSchemaTables(const QStringList &tables, const QSet<QString>& virtualTables, bool sort);
+ QList<QStandardItem*> refreshSchemaTableColumns(const QStringList& columns);
+ QList<QStandardItem*> refreshSchemaIndexes(const QStringList& indexes, bool sort);
+ QList<QStandardItem*> refreshSchemaTriggers(const QStringList& triggers, bool sort);
QList<QStandardItem*> refreshSchemaViews(const QStringList &views, bool sort);
void populateChildItemsWithDb(QStandardItem* parentItem, Db* db);
- void refreshSchemaBuild(QStandardItem* dbItem, QList<QStandardItem*> tables, StrHash<QList<QStandardItem*> > indexes,
- StrHash<QList<QStandardItem*> > triggers, QList<QStandardItem*> views, StrHash<QList<QStandardItem*> > allTableColumns);
+ void loadTableSchema(DbTreeItem* tableItem);
+ void loadViewSchema(DbTreeItem* viewItem);
+ void refreshSchemaBuild(QStandardItem* dbItem, QList<QStandardItem*> tables, QList<QStandardItem*> views);
void restoreExpandedState(const QHash<QString, bool>& expandedState, QStandardItem* parentItem);
- DbTreeItem* findFirstItemOfType(DbTreeItem::Type type, QStandardItem* parentItem);
QString getToolTip(DbTreeItem *item) const;
QString getDbToolTip(DbTreeItem *item) const;
QString getTableToolTip(DbTreeItem *item) const;
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.cpp
index a217da6..cf5848a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.cpp
@@ -9,11 +9,13 @@
#include "constraints/constraintpanel.h"
#include "datatype.h"
#include "uiutils.h"
+#include "common/dialogsizehandler.h"
#include <QDebug>
#include <QCheckBox>
#include <QMessageBox>
#include <QDebug>
#include <QPushButton>
+#include <schemaresolver.h>
ColumnDialog::ColumnDialog(Db* db, QWidget *parent) :
QDialog(parent),
@@ -33,6 +35,7 @@ void ColumnDialog::init()
ui->setupUi(this);
limitDialogWidth(this);
setWindowIcon(ICONS.COLUMN);
+ DialogSizeHandler::applyFor(this);
ui->scale->setStrict(true, true);
ui->precision->setStrict(true, true);
@@ -403,7 +406,7 @@ void ColumnDialog::updateTypeValidations()
setValidState(ui->typeCombo, typeOk, typeErrorMsg);
if (typeOk && integerTypeEnforced)
- setValidStateTooltip(ui->typeCombo, integerEnforcedMsg);
+ setValidStateTooltip(ui->typeCombo, integerEnforcedMsg);
if (!scaleOk || !precisionOk || !typeOk)
{
@@ -437,6 +440,43 @@ bool ColumnDialog::hasAutoIncr() const
return false;
}
+void ColumnDialog::validateFkTypeMatch()
+{
+ QString fkTypeWarningMsg = tr("Referenced column type (%1) is different than type declared in this column. It may cause issues while inserting or updating data.");
+
+ for (SqliteCreateTable::Column::Constraint*& constr : column->getConstraints(SqliteCreateTable::Column::Constraint::FOREIGN_KEY))
+ {
+ if (!constr->foreignKey || constr->foreignKey->indexedColumns.isEmpty() || constr->foreignKey->foreignTable.isNull())
+ continue;
+
+ QString fkTable = constr->foreignKey->foreignTable;
+ QString fkColumn = constr->foreignKey->indexedColumns.first()->name;
+ if (!fkTableTypesCache.contains(fkTable, Qt::CaseInsensitive))
+ {
+ SchemaResolver resolver(db);
+ fkTableTypesCache[fkTable] = resolver.getTableColumnDataTypesByName(fkTable);;
+ }
+
+ StrHash<DataType> fkTypes = fkTableTypesCache.value(fkTable, Qt::CaseInsensitive);
+ if (fkTypes.isEmpty())
+ continue;
+
+ DataType fkType = fkTypes.value(fkColumn, Qt::CaseInsensitive);
+ if (fkType.toString().toLower().trimmed() != ui->typeCombo->currentText().toLower().trimmed())
+ {
+ auto fkButton = getToolButtonForConstraint(constr);
+ if (!fkButton)
+ continue;
+
+ if (isValidStateIndicatorVisible(fkButton))
+ continue;
+
+ setValidStateWarning(fkButton, fkTypeWarningMsg.arg(fkType.toString()));
+ break;
+ }
+ }
+}
+
void ColumnDialog::moveConstraintUp()
{
QModelIndex idx = ui->constraintsView->currentIndex();
@@ -618,6 +658,7 @@ void ColumnDialog::updateValidations()
updateConstraint(constr);
updateTypeValidations();
+ validateFkTypeMatch();
}
void ColumnDialog::updateConstraint(SqliteCreateTable::Column::Constraint* constraint)
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.h b/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.h
index c9faf23..bc02d14 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.h
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/columndialog.h
@@ -5,6 +5,7 @@
#include "common/extactioncontainer.h"
#include "constraintdialog.h"
#include "guiSQLiteStudio_global.h"
+#include "common/strhash.h"
#include <QDialog>
#include <QPointer>
@@ -71,6 +72,7 @@ class GUI_API_EXPORT ColumnDialog : public QDialog, public ExtActionContainer
void updateTypeValidations();
void updateTypeForAutoIncr();
bool hasAutoIncr() const;
+ void validateFkTypeMatch();
Ui::ColumnDialog *ui = nullptr;
SqliteCreateTable::ColumnPtr column;
@@ -79,6 +81,7 @@ class GUI_API_EXPORT ColumnDialog : public QDialog, public ExtActionContainer
Db* db = nullptr;
bool integerTypeEnforced = false;
QSet<ConstraintDialog::Constraint> disabledConstraints;
+ StrHash<StrHash<DataType>> fkTableTypesCache;
private slots:
void updateConstraintsToolbarState();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/configdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/configdialog.cpp
index 8c80f6d..425acad 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/configdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/configdialog.cpp
@@ -28,6 +28,7 @@
#include "syntaxhighlighterplugin.h"
#include "sqleditor.h"
#include "style.h"
+#include "common/dialogsizehandler.h"
#include <QSignalMapper>
#include <QLineEdit>
#include <QSpinBox>
@@ -201,6 +202,7 @@ void ConfigDialog::init()
{
ui->setupUi(this);
setWindowIcon(ICONS.CONFIGURE);
+ DialogSizeHandler::applyFor(this);
ui->categoriesTree->setCurrentItem(ui->categoriesTree->topLevelItem(0));
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/constraintdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/constraintdialog.cpp
index 0333cbc..84c4cdc 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/constraintdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/constraintdialog.cpp
@@ -79,6 +79,8 @@ void ConstraintDialog::init()
}
currentPanel->setDb(db);
+ currentPanel->setCreateTableStmt(createTable.data());
+ currentPanel->setColumnStmt(columnStmt.data());
currentPanel->setConstraint(constrStatement);
connect(currentPanel, SIGNAL(updateValidation()), this, SLOT(validate()));
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.cpp
index e6a53db..2b85be3 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.cpp
@@ -145,6 +145,8 @@ void DbDialog::init()
ui->testConnIcon->setVisible(false);
+ connect(ui->existingDatabaseRadio, SIGNAL(clicked()), this, SLOT(updateCreateMode()));
+ connect(ui->createDatabaseRadio, SIGNAL(clicked()), this, SLOT(updateCreateMode()));
connect(ui->fileEdit, SIGNAL(textChanged(QString)), this, SLOT(fileChanged(QString)));
connect(ui->nameEdit, SIGNAL(textEdited(QString)), this, SLOT(nameModified(QString)));
connect(ui->browseOpenButton, SIGNAL(clicked()), this, SLOT(browseClicked()));
@@ -172,7 +174,9 @@ void DbDialog::updateOptions()
customBrowseHandler = nullptr;
ui->pathGroup->setTitle(tr("File"));
- ui->browseOpenButton->setToolTip(tr("Select new or existing file on local computer"));
+ ui->existingDatabaseRadio->setChecked(true);
+ ui->createDatabaseRadio->setChecked(false);
+ updateCreateMode();
optionWidgets.clear();
optionKeyToWidget.clear();
@@ -209,6 +213,10 @@ void DbDialog::addOption(const DbPluginOption& option, int& row)
// This option does not add any editor, but has it's own label for path edit.
row--;
ui->pathGroup->setTitle(option.label);
+ ui->existingDatabaseRadio->setChecked(true);
+ ui->createDatabaseRadio->setChecked(false);
+ ui->createDatabaseRadio->setVisible(false);
+ updateCreateMode();
if (!option.toolTip.isEmpty())
ui->browseOpenButton->setToolTip(option.toolTip);
@@ -567,6 +575,13 @@ bool DbDialog::validate()
setValidState(ui->fileEdit, false, tr("Enter a database file path."));
fileState = false;
}
+ else if (QFileInfo(getPath()).isRelative())
+ {
+ setValidStateWarning(ui->fileEdit,
+ tr("You're using a relative file path, which will be resolved to \"%1\" according to the application's working directory. It's always better to use absolute file path to avoid unexpected database location.")
+ .arg(QFileInfo(getPath()).absoluteFilePath()));
+ fileState = false;
+ }
if (fileState)
{
@@ -689,7 +704,7 @@ void DbDialog::browseClicked()
else
dir = getFileDialogInitPath();
- QString path = getDbPath(dir);
+ QString path = getDbPath(createMode, dir);
if (path.isNull())
return;
@@ -728,6 +743,15 @@ void DbDialog::nameModified(const QString &value)
updateState();
}
+void DbDialog::updateCreateMode()
+{
+ createMode = ui->createDatabaseRadio->isChecked();
+ ui->browseOpenButton->setToolTip(
+ createMode ? tr("Choose a location for the new database file")
+ : tr("Browse for existing database file on local computer")
+ );
+}
+
void DbDialog::accept()
{
QString name = getName();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.h b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.h
index 76cd3ec..a52734b 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.h
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.h
@@ -74,6 +74,7 @@ class GUI_API_EXPORT DbDialog : public QDialog
bool disableTypeAutodetection = false;
bool doAutoTest = false;
bool nameManuallyEdited = false;
+ bool createMode = false;
ImmediateTooltip* connIconTooltip = nullptr;
static const constexpr int ADDITIONAL_ROWS_BEGIN_INDEX = 1;
@@ -88,6 +89,7 @@ class GUI_API_EXPORT DbDialog : public QDialog
void propertyChanged();
void dbTypeChanged(int index);
void nameModified(const QString &value);
+ void updateCreateMode();
public slots:
void accept();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.ui b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.ui
index f0ebe2a..880175f 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.ui
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/dbdialog.ui
@@ -44,21 +44,42 @@
<property name="title">
<string>File</string>
</property>
- <layout class="QHBoxLayout" name="horizontalLayout_5">
+ <layout class="QVBoxLayout" name="verticalLayout_3">
<item>
- <widget class="QLineEdit" name="fileEdit"/>
+ <widget class="QRadioButton" name="existingDatabaseRadio">
+ <property name="text">
+ <string>Select an existing database file</string>
+ </property>
+ <property name="checked">
+ <bool>true</bool>
+ </property>
+ </widget>
</item>
<item>
- <widget class="QToolButton" name="browseOpenButton">
+ <widget class="QRadioButton" name="createDatabaseRadio">
<property name="text">
- <string/>
- </property>
- <property name="icon">
- <iconset resource="../icons.qrc">
- <normaloff>:/icons/img/open_sql_file.png</normaloff>:/icons/img/open_sql_file.png</iconset>
+ <string>Create a new database file</string>
</property>
</widget>
</item>
+ <item>
+ <layout class="QHBoxLayout" name="horizontalLayout_5">
+ <item>
+ <widget class="QLineEdit" name="fileEdit"/>
+ </item>
+ <item>
+ <widget class="QToolButton" name="browseOpenButton">
+ <property name="text">
+ <string/>
+ </property>
+ <property name="icon">
+ <iconset resource="../icons.qrc">
+ <normaloff>:/icons/img/open_sql_file.png</normaloff>:/icons/img/open_sql_file.png</iconset>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
</layout>
</widget>
</item>
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/ddlpreviewdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/ddlpreviewdialog.cpp
index 3af221f..f3863c8 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/ddlpreviewdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/ddlpreviewdialog.cpp
@@ -4,6 +4,7 @@
#include "uiconfig.h"
#include "sqlitestudio.h"
#include "db/db.h"
+#include "common/dialogsizehandler.h"
DdlPreviewDialog::DdlPreviewDialog(Db* db, QWidget *parent) :
QDialog(parent),
@@ -11,6 +12,7 @@ DdlPreviewDialog::DdlPreviewDialog(Db* db, QWidget *parent) :
db(db)
{
ui->setupUi(this);
+ DialogSizeHandler::applyFor(this);
}
DdlPreviewDialog::~DdlPreviewDialog()
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/exportdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/exportdialog.cpp
index 135bc9d..820e4cc 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/exportdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/exportdialog.cpp
@@ -16,6 +16,7 @@
#include "services/notifymanager.h"
#include "themetuner.h"
#include "uiconfig.h"
+#include "common/dialogsizehandler.h"
#include <QClipboard>
#include <QDebug>
#include <QDir>
@@ -52,6 +53,7 @@ void ExportDialog::init()
ui->setupUi(this);
THEME_TUNER->darkThemeFix(this);
limitDialogWidth(this);
+ DialogSizeHandler::applyFor(this);
#ifdef Q_OS_MACX
resize(width() + 150, height());
@@ -61,7 +63,9 @@ void ExportDialog::init()
widgetCover = new WidgetCover(this);
widgetCover->initWithInterruptContainer(tr("Cancel"));
connect(widgetCover, SIGNAL(cancelClicked()), EXPORT_MANAGER, SLOT(interrupt()));
+ connect(EXPORT_MANAGER, SIGNAL(finishedStep(int)), widgetCover, SLOT(setProgress(int)));
widgetCover->setVisible(false);
+ widgetCover->displayProgress(0, "%v");
initPageOrder();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/importdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/importdialog.cpp
index f443f18..6c9c8c7 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/importdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/importdialog.cpp
@@ -13,6 +13,7 @@
#include "themetuner.h"
#include "iconmanager.h"
#include "mainwindow.h"
+#include "common/dialogsizehandler.h"
#include <QDir>
#include <QDebug>
#include <QFileDialog>
@@ -102,6 +103,7 @@ void ImportDialog::init()
ui->setupUi(this);
THEME_TUNER->darkThemeFix(this);
limitDialogWidth(this);
+ DialogSizeHandler::applyFor(this);
#ifdef Q_OS_MACX
resize(width() + 150, height());
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/indexdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/indexdialog.cpp
index d5249d0..ad56f64 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/indexdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/indexdialog.cpp
@@ -13,6 +13,7 @@
#include "indexexprcolumndialog.h"
#include "windows/editorwindow.h"
#include "services/codeformatter.h"
+#include "common/dialogsizehandler.h"
#include <QDebug>
#include <QGridLayout>
#include <QSignalMapper>
@@ -64,6 +65,7 @@ void IndexDialog::init()
{
ui->setupUi(this);
limitDialogWidth(this);
+ DialogSizeHandler::applyFor(this);
if (!db || !db->isOpen())
{
qCritical() << "Created IndexDialog for null or closed database.";
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/populatedialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/populatedialog.cpp
index 89fff04..734f813 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/populatedialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/populatedialog.cpp
@@ -11,6 +11,7 @@
#include "services/populatemanager.h"
#include "common/widgetcover.h"
#include "common/compatibility.h"
+#include "common/dialogsizehandler.h"
#include <QPushButton>
#include <QGridLayout>
#include <QCheckBox>
@@ -45,6 +46,7 @@ void PopulateDialog::init()
{
ui->setupUi(this);
limitDialogWidth(this);
+ DialogSizeHandler::applyFor(this);
ui->buttonBox->button(QDialogButtonBox::Ok)->setText(tr("Populate", "populate dialog button"));
plugins = PLUGINS->getLoadedPlugins<PopulatePlugin>();
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/searchtextdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/searchtextdialog.cpp
index 578a253..b8992b4 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/searchtextdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/searchtextdialog.cpp
@@ -2,12 +2,14 @@
#include "ui_searchtextdialog.h"
#include "searchtextlocator.h"
#include "common/unused.h"
+#include "common/dialogsizehandler.h"
SearchTextDialog::SearchTextDialog(SearchTextLocator* textLocator, QWidget *parent) :
QDialog(parent),
ui(new Ui::SearchTextDialog), textLocator(textLocator)
{
ui->setupUi(this);
+ DialogSizeHandler::applyFor(this);
connect(textLocator, SIGNAL(replaceAvailable(bool)), this, SLOT(setReplaceAvailable(bool)));
connect(ui->findEdit, SIGNAL(textChanged(QString)), this, SLOT(markModifiedState()));
connect(ui->caseSensitiveCheck, SIGNAL(toggled(bool)), this, SLOT(markModifiedState()));
diff --git a/SQLiteStudio3/guiSQLiteStudio/dialogs/triggerdialog.cpp b/SQLiteStudio3/guiSQLiteStudio/dialogs/triggerdialog.cpp
index 5091613..61fdadd 100644
--- a/SQLiteStudio3/guiSQLiteStudio/dialogs/triggerdialog.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/dialogs/triggerdialog.cpp
@@ -13,6 +13,7 @@
#include "services/config.h"
#include "uiutils.h"
#include "services/codeformatter.h"
+#include "common/dialogsizehandler.h"
#include <QDebug>
#include <QMessageBox>
#include <QPushButton>
@@ -83,6 +84,7 @@ void TriggerDialog::init()
{
ui->setupUi(this);
limitDialogWidth(this);
+ DialogSizeHandler::applyFor(this);
connect(ui->tabWidget, SIGNAL(currentChanged(int)), this, SLOT(updateDdlTab(int)));
connect(ui->actionColumns, SIGNAL(clicked()), this, SLOT(showColumnsDialog()));
diff --git a/SQLiteStudio3/guiSQLiteStudio/extendedpalette.cpp b/SQLiteStudio3/guiSQLiteStudio/extendedpalette.cpp
index eba2f4c..28edbe3 100644
--- a/SQLiteStudio3/guiSQLiteStudio/extendedpalette.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/extendedpalette.cpp
@@ -31,10 +31,11 @@ bool ExtendedPalette::styleChanged(QStyle *style, const QString &themeName)
{
UNUSED(themeName);
QPalette stdPalette = style->standardPalette();
- if (stdPalette == lastPalette)
+ QVariant paletteVariant = stdPalette;
+ if (paletteVariant == initializedForPalette)
return false;
- lastPalette = stdPalette;
+ initializedForPalette = paletteVariant;
bool isDark = stdPalette.base().color().lightness() < 128;
static const QColor stdStrColor = QColor(Qt::green);
diff --git a/SQLiteStudio3/guiSQLiteStudio/extendedpalette.h b/SQLiteStudio3/guiSQLiteStudio/extendedpalette.h
index 6afaeba..0891ce7 100644
--- a/SQLiteStudio3/guiSQLiteStudio/extendedpalette.h
+++ b/SQLiteStudio3/guiSQLiteStudio/extendedpalette.h
@@ -3,6 +3,7 @@
#include <QBrush>
#include <QPalette>
+#include <QVariant>
class QStyle;
@@ -39,7 +40,7 @@ class ExtendedPalette
QBrush editorCurrentQueryBrush;
QBrush mdiAreaBaseBrush;
- QPalette lastPalette;
+ QVariant initializedForPalette;
};
#endif // EXTENDEDPALETTE_H
diff --git a/SQLiteStudio3/guiSQLiteStudio/guiSQLiteStudio.pro b/SQLiteStudio3/guiSQLiteStudio/guiSQLiteStudio.pro
index 9a436de..fde6802 100644
--- a/SQLiteStudio3/guiSQLiteStudio/guiSQLiteStudio.pro
+++ b/SQLiteStudio3/guiSQLiteStudio/guiSQLiteStudio.pro
@@ -33,10 +33,12 @@ DEFINES += GUISQLITESTUDIO_LIBRARY
SOURCES +=\
common/dbcombobox.cpp \
+ common/dialogsizehandler.cpp \
common/immediatetooltip.cpp \
common/mouseshortcut.cpp \
constraints/columngeneratedpanel.cpp \
datagrid/fkcombobox.cpp \
+ datagrid/sqlqueryitemlineedit.cpp \
extendedpalette.cpp \
mainwindow.cpp \
iconmanager.cpp \
@@ -193,10 +195,12 @@ SOURCES +=\
HEADERS += mainwindow.h \
common/dbcombobox.h \
+ common/dialogsizehandler.h \
common/immediatetooltip.h \
common/mouseshortcut.h \
constraints/columngeneratedpanel.h \
datagrid/fkcombobox.h \
+ datagrid/sqlqueryitemlineedit.h \
extendedpalette.h \
iconmanager.h \
dbtree/dbtreemodel.h \
diff --git a/SQLiteStudio3/guiSQLiteStudio/sqleditor.cpp b/SQLiteStudio3/guiSQLiteStudio/sqleditor.cpp
index d1f1a47..1fb57ec 100644
--- a/SQLiteStudio3/guiSQLiteStudio/sqleditor.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/sqleditor.cpp
@@ -25,6 +25,8 @@
#include "dbtree/dbtreeview.h"
#include "common/lazytrigger.h"
#include "common/extaction.h"
+#include "db/dbsqlite3.h"
+#include "dialogs/dbdialog.h"
#include <QAction>
#include <QMenu>
#include <QTimer>
@@ -35,6 +37,7 @@
#include <QScrollBar>
#include <QFileDialog>
#include <QtConcurrent/QtConcurrent>
+#include <QMessageBox>
#include <QStyle>
CFG_KEYS_DEFINE(SqlEditor)
@@ -727,6 +730,9 @@ void SqlEditor::highlightParenthesis(QList<QTextEdit::ExtraSelection>& selection
void SqlEditor::highlightCurrentQuery(QList<QTextEdit::ExtraSelection>& selections)
{
+ if (!richFeaturesEnabled)
+ return;
+
QTextCursor cursor = textCursor();
int curPos = cursor.position();
QString contents = cursor.document()->toPlainText();
@@ -735,7 +741,7 @@ void SqlEditor::highlightCurrentQuery(QList<QTextEdit::ExtraSelection>& selectio
return;
QTextEdit::ExtraSelection selection;
- selection.format.setBackground(STYLE->extendedPalette().editorCurrentQueryBase());
+ selection.format.setBackground(Cfg::getSyntaxCurrentQueryBg());
cursor.setPosition(boundries.first);
cursor.setPosition(boundries.second, QTextCursor::KeepAnchor);
@@ -1100,7 +1106,7 @@ void SqlEditor::highlightCurrentLine(QList<QTextEdit::ExtraSelection>& selection
if (!isReadOnly() && isEnabled())
{
QTextEdit::ExtraSelection selection;
- selection.format.setBackground(STYLE->extendedPalette().editorLineBase());
+ selection.format.setBackground(Cfg::getSyntaxCurrentLineBg());
selection.format.setProperty(QTextFormat::FullWidthSelection, true);
selection.cursor = textCursor();
selection.cursor.clearSelection();
@@ -1197,6 +1203,24 @@ void SqlEditor::loadFromFile()
setFileDialogInitPathByFile(fName);
+ if (DbSqlite3::isDbFile(fName))
+ {
+ DbDialog dialog(DbDialog::ADD, MAINWINDOW);
+ dialog.setPath(fName);
+ dialog.setDoAutoTest(true);
+ dialog.exec();
+ return;
+ }
+
+ if (QFile(fName).size() > HUGE_QUERY_LENGTH)
+ {
+ QMessageBox::StandardButton resp = QMessageBox::question(this, tr("Open file"),
+ tr("This file is huge (over %1 MB). Are you sure you want to load it into SQL query editor?")
+ .arg(HUGE_QUERY_LENGTH / 1024 / 1024));
+ if (resp != QMessageBox::Yes)
+ return;
+ }
+
QString err;
QString sql = readFileContents(fName, &err);
if (sql.isNull() && !err.isNull())
@@ -1205,9 +1229,13 @@ void SqlEditor::loadFromFile()
return;
}
- setPlainText(sql);
-
- loadedFile = fName;
+ if (toPlainText().trimmed().isEmpty())
+ {
+ setPlainText(sql);
+ loadedFile = fName;
+ }
+ else
+ MAINWINDOW->openSqlEditor(db, sql);
}
void SqlEditor::deleteLine()
@@ -1715,10 +1743,11 @@ void SqlEditor::saveSelection()
}
void SqlEditor::restoreSelection()
-{
+{
QTextCursor cur = textCursor();
cur.setPosition(storedSelectionStart);
cur.setPosition(storedSelectionEnd, QTextCursor::KeepAnchor);
+ setTextCursor(cur);
}
QToolBar* SqlEditor::getToolBar(int toolbar) const
diff --git a/SQLiteStudio3/guiSQLiteStudio/sqleditor.h b/SQLiteStudio3/guiSQLiteStudio/sqleditor.h
index 4af89c1..b78b46b 100644
--- a/SQLiteStudio3/guiSQLiteStudio/sqleditor.h
+++ b/SQLiteStudio3/guiSQLiteStudio/sqleditor.h
@@ -124,6 +124,8 @@ class GUI_API_EXPORT SqlEditor : public QPlainTextEdit, public ExtActionContaine
bool getAlwaysEnforceErrorsChecking() const;
void setAlwaysEnforceErrorsChecking(bool newAlwaysEnforceErrorsChecking);
+ static constexpr int HUGE_QUERY_LENGTH = 10 * 1024 * 1024; // 10MB of SQL
+
protected:
void setupDefShortcuts();
void createActions();
diff --git a/SQLiteStudio3/guiSQLiteStudio/taskbar.cpp b/SQLiteStudio3/guiSQLiteStudio/taskbar.cpp
index 2e6a93a..8f3936e 100644
--- a/SQLiteStudio3/guiSQLiteStudio/taskbar.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/taskbar.cpp
@@ -55,6 +55,18 @@ QList<QAction*> TaskBar::getTasks() const
void TaskBar::init()
{
setAcceptDrops(true);
+ setStyleSheet(R"(
+ QToolButton:checked {
+ color: white;
+ background-color: #0078D7;
+ border: 2px solid #005A9E;
+ border-radius: 4px;
+ }
+ QToolButton:hover {
+ background-color: #005A9E;
+ color: white;
+ }
+ )");
}
void TaskBar::mousePressed()
diff --git a/SQLiteStudio3/guiSQLiteStudio/translations/guiSQLiteStudio_de_DE.ts b/SQLiteStudio3/guiSQLiteStudio/translations/guiSQLiteStudio_de_DE.ts
index de05638..a732e3d 100644
--- a/SQLiteStudio3/guiSQLiteStudio/translations/guiSQLiteStudio_de_DE.ts
+++ b/SQLiteStudio3/guiSQLiteStudio/translations/guiSQLiteStudio_de_DE.ts
@@ -5321,13 +5321,13 @@ find next</source>
<location filename="../sqleditor.cpp" line="165"/>
<source>Select file to save SQL</source>
<comment>sql editor</comment>
- <translation>SQL aus Datei laden</translation>
+ <translation>Datei zum Speichern von SQL auswählen</translation>
</message>
<message>
<location filename="../sqleditor.cpp" line="166"/>
<source>Load SQL from file</source>
<comment>sql editor</comment>
- <translation>Zeile löschen</translation>
+ <translation>SQL aus Datei laden</translation>
</message>
<message>
<location filename="../sqleditor.cpp" line="167"/>
diff --git a/SQLiteStudio3/guiSQLiteStudio/uiutils.cpp b/SQLiteStudio3/guiSQLiteStudio/uiutils.cpp
index a73b8ee..cdad77c 100644
--- a/SQLiteStudio3/guiSQLiteStudio/uiutils.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/uiutils.cpp
@@ -35,7 +35,7 @@ const QStringList pageSizes = map<QPageSize::PageSizeId, QString>(pageSizeIds, [
const QStringList pageSizesWithDimensions;
-QString getDbPath(const QString &startWith)
+QString getDbPath(bool newFileMode, const QString &startWith)
{
QString dir = startWith;
if (dir.isNull())
@@ -48,8 +48,15 @@ QString getDbPath(const QString &startWith)
});
QFileDialog dialog(nullptr, QObject::tr("Select database file"), dir, QString());
- dialog.setAcceptMode(QFileDialog::AcceptOpen);
+ dialog.setAcceptMode(newFileMode ? QFileDialog::AcceptSave : QFileDialog::AcceptOpen);
+
+ /* As we don't actually overwrite a selected existing database file, switch off the
+ * overwrite warning.
+ * FIXME: QFileDialog::DontConfirmOverwrite does not work on MacOS native dialogs.
+ * Probably some better UX is needed.
+ */
dialog.setOption(QFileDialog::DontConfirmOverwrite, true);
+
dialog.setLabelText(QFileDialog::Accept, QObject::tr("Select"));
dialog.setLabelText(QFileDialog::FileType, QObject::tr("File type"));
dialog.setNameFilters(filters);
@@ -97,6 +104,11 @@ void setValidStateTooltip(QWidget* widget, const QString& tip)
INDICATOR(widget)->setVisible(widget->isEnabled(), tip);
}
+bool isValidStateIndicatorVisible(QWidget* widget)
+{
+ return EXISTS_INDICATOR(widget) && INDICATOR(widget)->isVisible();
+}
+
QString convertPageSize(QPageSize::PageSizeId size)
{
return QPageSize::name(size);
diff --git a/SQLiteStudio3/guiSQLiteStudio/uiutils.h b/SQLiteStudio3/guiSQLiteStudio/uiutils.h
index 324ed9e..c08cb0b 100644
--- a/SQLiteStudio3/guiSQLiteStudio/uiutils.h
+++ b/SQLiteStudio3/guiSQLiteStudio/uiutils.h
@@ -8,12 +8,13 @@
class QWidget;
class QToolBar;
-GUI_API_EXPORT QString getDbPath(const QString& startWith = QString());
+GUI_API_EXPORT QString getDbPath(bool newFileMode, const QString& startWith = QString());
GUI_API_EXPORT void setValidState(QWidget* widget, bool valid, const QString& message = QString());
GUI_API_EXPORT void setValidStateWihtTooltip(QWidget* widget, const QString& tooltip, bool valid, const QString& message = QString());
GUI_API_EXPORT void setValidStateWarning(QWidget* widget, const QString& warning);
GUI_API_EXPORT void setValidStateInfo(QWidget* widget, const QString& info);
GUI_API_EXPORT void setValidStateTooltip(QWidget* widget, const QString& tip);
+GUI_API_EXPORT bool isValidStateIndicatorVisible(QWidget* widget);
GUI_API_EXPORT const QStringList& getAllPageSizes();
GUI_API_EXPORT QString convertPageSize(QPageSize::PageSizeId size);
GUI_API_EXPORT QPageSize convertPageSize(const QString& size);
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.cpp
index df72db2..6624bc5 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.cpp
@@ -105,14 +105,14 @@ void CollationsEditor::init()
connect(ui->nameEdit, SIGNAL(textChanged(QString)), this, SLOT(updateModified()));
connect(ui->allDatabasesRadio, SIGNAL(clicked()), this, SLOT(updateModified()));
connect(ui->selectedDatabasesRadio, SIGNAL(clicked()), this, SLOT(updateModified()));
+ connect(ui->functionBasedRadio, SIGNAL(clicked()), this, SLOT(updateModified()));
+ connect(ui->extensionBasedRadio, SIGNAL(clicked()), this, SLOT(updateModified()));
connect(ui->langCombo, SIGNAL(currentTextChanged(QString)), this, SLOT(updateModified()));
connect(dbListModel, SIGNAL(dataChanged(QModelIndex,QModelIndex)), this, SLOT(updateModified()));
connect(CFG_UI.Fonts.SqlEditor, SIGNAL(changed(QVariant)), this, SLOT(changeFont(QVariant)));
- // Language plugins
- for (ScriptingPlugin* plugin : PLUGINS->getLoadedPlugins<ScriptingPlugin>())
- ui->langCombo->addItem(plugin->getLanguage());
+ updateLangCombo();
// Syntax highlighting plugins
for (SyntaxHighlighterPlugin* plugin : PLUGINS->getLoadedPlugins<SyntaxHighlighterPlugin>())
@@ -130,9 +130,16 @@ int CollationsEditor::getCurrentCollationRow() const
return idxList.first().row();
}
+CollationManager::CollationType CollationsEditor::getCurrentType() const
+{
+ return ui->extensionBasedRadio->isChecked() ? CollationManager::CollationType::EXTENSION_BASED
+ : CollationManager::CollationType::FUNCTION_BASED;
+}
+
void CollationsEditor::collationDeselected(int row)
{
model->setName(row, ui->nameEdit->text());
+ model->setType(row, getCurrentType());
model->setLang(row, ui->langCombo->currentText());
model->setAllDatabases(row, ui->allDatabasesRadio->isChecked());
model->setCode(row, ui->codeEdit->toPlainText());
@@ -149,6 +156,9 @@ void CollationsEditor::collationSelected(int row)
updatesForSelection = true;
ui->nameEdit->setText(model->getName(row));
ui->codeEdit->setPlainText(model->getCode(row));
+ ui->functionBasedRadio->setChecked(model->getType(row) == CollationManager::CollationType::FUNCTION_BASED);
+ ui->extensionBasedRadio->setChecked(model->getType(row) == CollationManager::CollationType::EXTENSION_BASED);
+ updateLangCombo();
ui->langCombo->setCurrentText(model->getLang(row));
// Databases
@@ -238,7 +248,7 @@ void CollationsEditor::newCollation()
CollationManager::CollationPtr coll = CollationManager::CollationPtr::create();
coll->name = generateUniqueName("collation", model->getCollationNames());
-
+ coll->type = getCurrentType();
if (ui->langCombo->currentIndex() > -1)
coll->lang = ui->langCombo->currentText();
@@ -287,6 +297,8 @@ void CollationsEditor::updateCurrentCollationState()
bool nameOk = model->isAllowedName(row, name) && !name.trimmed().isEmpty();
setValidState(ui->nameEdit, nameOk, tr("Enter a non-empty, unique name of the collation."));
+ updateLangCombo();
+
bool langOk = ui->langCombo->currentIndex() >= 0;
ui->codeGroup->setEnabled(langOk);
ui->databasesGroup->setEnabled(langOk);
@@ -296,7 +308,16 @@ void CollationsEditor::updateCurrentCollationState()
setValidState(ui->langCombo, langOk, tr("Pick the implementation language."));
bool codeOk = !ui->codeEdit->toPlainText().trimmed().isEmpty();
- setValidState(ui->codeEdit, codeOk, tr("Enter a non-empty implementation code."));
+ if (ui->extensionBasedRadio->isChecked())
+ {
+ ui->codeGroup->setTitle(tr("Registration code"));
+ setValidState(ui->codeEdit, codeOk, tr("Enter a non-empty registration code."));
+ }
+ else
+ {
+ ui->codeGroup->setTitle(tr("Implementation code"));
+ setValidState(ui->codeEdit, codeOk, tr("Enter a non-empty implementation code."));
+ }
// Syntax highlighter
QString lang = ui->langCombo->currentText();
@@ -343,6 +364,34 @@ void CollationsEditor::collationSelected(const QItemSelection& selected, const Q
}
}
+void CollationsEditor::updateLangCombo()
+{
+ QComboBox *combo = ui->langCombo;
+ bool alreadyInternalUpdate = updatesForSelection;
+ updatesForSelection = true;
+ if (ui->extensionBasedRadio->isChecked())
+ {
+ if (combo->isEnabled())
+ {
+ combo->setEnabled(false);
+ combo->clear();
+ combo->addItem("SQL");
+ combo->setCurrentIndex(0);
+ }
+ }
+ else
+ {
+ if (!combo->isEnabled())
+ {
+ combo->clear();
+ for (ScriptingPlugin* plugin : PLUGINS->getLoadedPlugins<ScriptingPlugin>())
+ combo->addItem(plugin->getLanguage());
+ combo->setEnabled(true);
+ }
+ }
+ updatesForSelection = alreadyInternalUpdate;
+}
+
void CollationsEditor::updateModified()
{
if (updatesForSelection)
@@ -353,11 +402,12 @@ void CollationsEditor::updateModified()
{
bool nameDiff = model->getName(row) != ui->nameEdit->text();
bool codeDiff = model->getCode(row) != ui->codeEdit->toPlainText();
+ bool typeDiff = model->getType(row) != getCurrentType();
bool langDiff = model->getLang(row) != ui->langCombo->currentText();
bool allDatabasesDiff = model->getAllDatabases(row) != ui->allDatabasesRadio->isChecked();
bool dbDiff = toSet(getCurrentDatabases()) != toSet(model->getDatabases(row)); // QSet to ignore order
- currentModified = (nameDiff || codeDiff || langDiff || allDatabasesDiff || dbDiff);
+ currentModified = (nameDiff || codeDiff || typeDiff || langDiff || allDatabasesDiff || dbDiff);
}
updateCurrentCollationState();
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.h b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.h
index 61c9165..7f61a82 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.h
@@ -3,6 +3,7 @@
#include "mdichild.h"
#include "common/extactioncontainer.h"
+#include "services/collationmanager.h"
#include <QItemSelection>
#include <QModelIndex>
#include <QWidget>
@@ -61,12 +62,14 @@ class GUI_API_EXPORT CollationsEditor : public MdiChild
private:
void init();
int getCurrentCollationRow() const;
+ CollationManager::CollationType getCurrentType() const;
void collationDeselected(int row);
void collationSelected(int row);
void clearEdits();
void selectCollation(int row);
QStringList getCurrentDatabases() const;
void setFont(const QFont& font);
+ void updateLangCombo();
Ui::CollationsEditor *ui = nullptr;
CollationsEditorModel* model = nullptr;
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.ui b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.ui
index 454c12a..123c2ba 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.ui
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditor.ui
@@ -203,13 +203,38 @@
<widget class="QLineEdit" name="nameEdit"/>
</item>
<item row="0" column="1">
+ <widget class="QLabel" name="typeLabel">
+ <property name="text">
+ <string>Collation type:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <layout class="QVBoxLayout" name="verticalLayout_6">
+ <item>
+ <widget class="QRadioButton" name="functionBasedRadio">
+ <property name="text">
+ <string>Function-based</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QRadioButton" name="extensionBasedRadio">
+ <property name="text">
+ <string>Extension-based</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item row="0" column="2">
<widget class="QLabel" name="langLabel">
<property name="text">
<string>Implementation language:</string>
</property>
</widget>
</item>
- <item row="1" column="1">
+ <item row="1" column="2">
<widget class="QComboBox" name="langCombo"/>
</item>
</layout>
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.cpp
index f04e023..0587d76 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.cpp
@@ -1,6 +1,7 @@
#include "collationseditormodel.h"
#include "common/unused.h"
#include "common/strhash.h"
+#include "iconmanager.h"
#include "services/pluginmanager.h"
#include "plugins/scriptingplugin.h"
#include "icon.h"
@@ -69,6 +70,16 @@ QString CollationsEditorModel::getName(int row) const
GETTER(collationList[row]->data->name, QString());
}
+void CollationsEditorModel::setType(int row, CollationManager::CollationType type)
+{
+ SETTER(collationList[row]->data->type, type);
+}
+
+CollationManager::CollationType CollationsEditorModel::getType(int row) const
+{
+ GETTER(collationList[row]->data->type, CollationManager::CollationType::FUNCTION_BASED);
+}
+
void CollationsEditorModel::setLang(int row, const QString& lang)
{
SETTER(collationList[row]->data->lang, lang);
@@ -248,13 +259,17 @@ QVariant CollationsEditorModel::data(const QModelIndex& index, int role) const
if (role == Qt::DisplayRole)
return collationList[index.row()]->data->name;
- if (role == Qt::DecorationRole && langToIcon.contains(collationList[index.row()]->data->lang))
+ if (role == Qt::DecorationRole)
{
- QIcon icon = langToIcon[collationList[index.row()]->data->lang];
- if (!collationList[index.row()]->valid)
- icon = Icon::merge(icon, Icon::ERROR);
-
- return icon;
+ auto coll = collationList[index.row()]->data;
+ bool isExtension = coll->type == CollationManager::CollationType::EXTENSION_BASED;
+ if (isExtension || langToIcon.contains(coll->lang))
+ {
+ QIcon icon = isExtension ? ICONS.EXTENSION : langToIcon[coll->lang];
+ if (!collationList[index.row()]->valid)
+ icon = Icon::merge(icon, Icon::ERROR);
+ return icon;
+ }
}
return QVariant();
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.h b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.h
index 46f7ab5..47b8b08 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/collationseditormodel.h
@@ -21,6 +21,8 @@ class GUI_API_EXPORT CollationsEditorModel : public QAbstractListModel
void setModified(int row, bool modified);
void setName(int row, const QString& name);
QString getName(int row) const;
+ void setType(int row, CollationManager::CollationType type);
+ CollationManager::CollationType getType(int row) const;
void setLang(int row, const QString& lang);
QString getLang(int row) const;
void setAllDatabases(int row, bool allDatabases);
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.cpp
index 23cb651..aa59bb0 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.cpp
@@ -211,7 +211,7 @@ QAction* EditorWindow::getAction(EditorWindow::Action action)
return ExtActionContainer::getAction(action);
}
-QString EditorWindow::getQueryToExecute(bool doSelectCurrentQuery, QueryExecMode querySelectionMode)
+QString EditorWindow::getQueryToExecute(QueryExecMode querySelectionMode)
{
QString sql;
if (ui->sqlEdit->textCursor().hasSelection())
@@ -228,9 +228,8 @@ QString EditorWindow::getQueryToExecute(bool doSelectCurrentQuery, QueryExecMode
ui->sqlEdit->saveSelection();
selectCurrentQuery(true);
sql = ui->sqlEdit->textCursor().selectedText();
+ ui->sqlEdit->restoreSelection();
fixTextCursorSelectedText(sql);
- if (!doSelectCurrentQuery)
- ui->sqlEdit->restoreSelection();
}
else
{
@@ -463,7 +462,7 @@ void EditorWindow::updateShortcutTips()
void EditorWindow::execQuery(bool explain, QueryExecMode querySelectionMode)
{
- QString sql = getQueryToExecute(true, querySelectionMode);
+ QString sql = getQueryToExecute(querySelectionMode);
QHash<QString, QVariant> bindParams;
bool proceed = processBindParams(sql, bindParams);
if (!proceed)
@@ -474,7 +473,7 @@ void EditorWindow::execQuery(bool explain, QueryExecMode querySelectionMode)
resultsModel->setQuery(sql);
resultsModel->setParams(bindParams);
resultsModel->setQueryCountLimitForSmartMode(queryLimitForSmartExecution);
- ui->dataView->refreshData();
+ ui->dataView->refreshData(false);
updateState();
if (resultsDisplayMode == ResultsDisplayMode::SEPARATE_TAB)
@@ -741,7 +740,7 @@ void EditorWindow::createViewFromQuery()
return;
}
- QString sql = getQueryToExecute(true);
+ QString sql = getQueryToExecute();
DbObjectDialogs dialogs(getCurrentDb());
dialogs.addView(sql);
}
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.h b/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.h
index 977784e..0ca2cdf 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/editorwindow.h
@@ -100,7 +100,7 @@ class GUI_API_EXPORT EditorWindow : public MdiChild
QSize sizeHint() const;
QAction* getAction(Action action);
- QString getQueryToExecute(bool doSelectCurrentQuery = false, QueryExecMode querySelectionMode = DEFAULT);
+ QString getQueryToExecute(QueryExecMode querySelectionMode = DEFAULT);
bool setCurrentDb(Db* db);
void setContents(const QString& sql);
QString getContents() const;
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.cpp
index 4d964c8..e349525 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.cpp
@@ -170,9 +170,12 @@ int FunctionsEditor::getCurrentFunctionRow() const
void FunctionsEditor::functionDeselected(int row)
{
model->setName(row, ui->nameEdit->text());
+ model->setUndefinedArgs(row, ui->undefArgsCheck->isChecked());
+ if (!ui->undefArgsCheck->isChecked())
+ model->setArguments(row, getCurrentArgList());
+
model->setLang(row, ui->langCombo->currentText());
model->setType(row, getCurrentFunctionType());
- model->setUndefinedArgs(row, ui->undefArgsCheck->isChecked());
model->setAllDatabases(row, ui->allDatabasesRadio->isChecked());
model->setCode(row, ui->mainCodeEdit->toPlainText());
model->setDeterministic(row, ui->deterministicCheck->isChecked());
@@ -189,9 +192,6 @@ void FunctionsEditor::functionDeselected(int row)
model->setFinalCode(row, QString());
}
- if (!ui->undefArgsCheck->isChecked())
- model->setArguments(row, getCurrentArgList());
-
if (ui->selDatabasesRadio->isChecked())
model->setDatabases(row, getCurrentDatabases());
@@ -416,8 +416,10 @@ void FunctionsEditor::updateCurrentFunctionState()
}
QString name = ui->nameEdit->text();
- bool nameOk = model->isAllowedName(row, name) && !name.trimmed().isEmpty();
- setValidState(ui->nameEdit, nameOk, tr("Enter a non-empty, unique name of the function."));
+ QStringList argList = getCurrentArgList();
+ bool undefArgs = ui->undefArgsCheck->isChecked();
+ bool nameOk = model->isAllowedName(row, name, argList, undefArgs) && !name.trimmed().isEmpty();
+ setValidState(ui->nameEdit, nameOk, tr("Enter a unique, non-empty function name. Duplicate names are allowed if the number of input parameters differs."));
bool langOk = ui->langCombo->currentIndex() >= 0;
ui->initCodeGroup->setEnabled(langOk);
@@ -488,8 +490,8 @@ void FunctionsEditor::updateCurrentFunctionState()
currentHighlighterLang = lang;
}
- updateArgsState();
- model->setValid(row, langOk && codeOk && finalCodeOk && nameOk);
+ bool argsOk = updateArgsState();
+ model->setValid(row, langOk && codeOk && finalCodeOk && nameOk && argsOk);
updateState();
}
@@ -576,7 +578,7 @@ void FunctionsEditor::moveFunctionArgDown()
ui->argsList->selectionModel()->setCurrentIndex(idx, QItemSelectionModel::Clear|QItemSelectionModel::SelectCurrent);
}
-void FunctionsEditor::updateArgsState()
+bool FunctionsEditor::updateArgsState()
{
bool argsEnabled = !ui->undefArgsCheck->isChecked();
QModelIndexList indexes = ui->argsList->selectionModel()->selectedIndexes();
@@ -596,6 +598,32 @@ void FunctionsEditor::updateArgsState()
actionMap[ARG_MOVE_UP]->setEnabled(argsEnabled && canMoveUp);
actionMap[ARG_MOVE_DOWN]->setEnabled(argsEnabled && canMoveDown);
ui->argsList->setEnabled(argsEnabled);
+
+ if (argsEnabled)
+ {
+ bool argsOk = true;
+ QSet<QString> usedNames;
+ for (int rowIdx = 0; rowIdx < ui->argsList->model()->rowCount(); rowIdx++)
+ {
+ QListWidgetItem* item = ui->argsList->item(rowIdx);
+ QString argName = item->text().toLower();
+ if (argName.isEmpty())
+ {
+ argsOk = false;
+ break;
+ }
+ if (usedNames.contains(argName))
+ {
+ argsOk = false;
+ break;
+ }
+ usedNames << argName;
+ }
+ setValidState(ui->argsList, argsOk, tr("Function argument cannot be empty and it cannot have duplicated name."));
+ return argsOk;
+ }
+ else
+ return true;
}
void FunctionsEditor::applyFilter(const QString& value)
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.h b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.h
index d3fcf12..d513234 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditor.h
@@ -105,7 +105,7 @@ class GUI_API_EXPORT FunctionsEditor : public MdiChild
void delFunctionArg();
void moveFunctionArgUp();
void moveFunctionArgDown();
- void updateArgsState();
+ bool updateArgsState();
void applyFilter(const QString& value);
void help();
void changeFont(const QVariant& font);
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.cpp
index 46ae8d9..13ec34f 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.cpp
@@ -266,16 +266,17 @@ QStringList FunctionsEditorModel::getFunctionNames() const
void FunctionsEditorModel::validateNames()
{
- StrHash<QList<int>> counter;
+ QHash<UniqueFunctionName, QList<int>> counter;
int row = 0;
for (Function*& func : functionList)
{
func->valid &= true;
- counter[func->data.name] << row++;
+ UniqueFunctionName uniqueName = func->toUniqueName();
+ counter[uniqueName] << row++;
}
- QHashIterator<QString,QList<int>> cntIt = counter.iterator();
+ QHashIterator<UniqueFunctionName, QList<int>> cntIt(counter);
while (cntIt.hasNext())
{
cntIt.next();
@@ -294,11 +295,18 @@ void FunctionsEditorModel::validateNames()
}
}
-bool FunctionsEditorModel::isAllowedName(int rowToSkip, const QString& nameToValidate)
+bool FunctionsEditorModel::isAllowedName(int rowToSkip, const QString& nameToValidate, const QStringList& argList, bool undefinedArgs)
{
- QStringList names = getFunctionNames();
+ QList<UniqueFunctionName> names = getUniqueFunctionNames();
names.removeAt(rowToSkip);
- return !names.contains(nameToValidate, Qt::CaseInsensitive);
+
+ UniqueFunctionName validatedName;
+ validatedName.name = nameToValidate.toLower();
+ validatedName.undefArg = undefinedArgs;
+ if (!undefinedArgs)
+ validatedName.arguments = argList;
+
+ return !names.contains(validatedName);
}
int FunctionsEditorModel::rowCount(const QModelIndex& parent) const
@@ -347,6 +355,15 @@ void FunctionsEditorModel::emitDataChanged(int row)
emit dataChanged(idx, idx);
}
+QList<FunctionsEditorModel::UniqueFunctionName> FunctionsEditorModel::getUniqueFunctionNames() const
+{
+ QList<UniqueFunctionName> names;
+ for (Function* func : functionList)
+ names << func->toUniqueName();
+
+ return names;
+}
+
FunctionsEditorModel::Function::Function()
{
}
@@ -356,3 +373,29 @@ FunctionsEditorModel::Function::Function(FunctionManager::ScriptFunction* other)
data = FunctionManager::ScriptFunction(*other);
originalName = data.name;
}
+
+FunctionsEditorModel::UniqueFunctionName FunctionsEditorModel::Function::toUniqueName() const
+{
+ UniqueFunctionName uniqName;
+ uniqName.name = data.name.toLower();
+ uniqName.undefArg = data.undefinedArgs;
+ if (!data.undefinedArgs)
+ uniqName.arguments = data.arguments;
+
+ return uniqName;
+}
+
+int FunctionsEditorModel::UniqueFunctionName::argCount() const
+{
+ return undefArg ? -1 : arguments.size();
+}
+
+bool FunctionsEditorModel::UniqueFunctionName::operator==(const UniqueFunctionName &other) const
+{
+ return name == other.name && argCount() == other.argCount();
+}
+
+int qHash(FunctionsEditorModel::UniqueFunctionName fnName)
+{
+ return qHash(fnName.name) ^ fnName.argCount();
+}
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.h b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.h
index 7caf06c..2f90bcc 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/functionseditormodel.h
@@ -60,17 +60,28 @@ class GUI_API_EXPORT FunctionsEditorModel : public QAbstractListModel
QList<FunctionManager::ScriptFunction*> generateFunctions() const;
QStringList getFunctionNames() const;
void validateNames();
- bool isAllowedName(int rowToSkip, const QString& nameToValidate);
+ bool isAllowedName(int rowToSkip, const QString& nameToValidate, const QStringList &argList, bool undefinedArgs);
bool isValidRowIndex(int row) const;
int rowCount(const QModelIndex& parent = QModelIndex()) const;
QVariant data(const QModelIndex& index, int role) const;
private:
+ struct UniqueFunctionName
+ {
+ QString name;
+ QStringList arguments;
+ bool undefArg;
+
+ int argCount() const;
+ bool operator==(const UniqueFunctionName& other) const;
+ };
+
struct Function
{
Function();
Function(FunctionManager::ScriptFunction* other);
+ UniqueFunctionName toUniqueName() const;
FunctionManager::ScriptFunction data;
bool modified = false;
@@ -80,6 +91,9 @@ class GUI_API_EXPORT FunctionsEditorModel : public QAbstractListModel
void init();
void emitDataChanged(int row);
+ QList<UniqueFunctionName> getUniqueFunctionNames() const;
+
+ friend int qHash(FunctionsEditorModel::UniqueFunctionName fnName);
QList<Function*> functionList;
@@ -96,4 +110,6 @@ class GUI_API_EXPORT FunctionsEditorModel : public QAbstractListModel
bool listModified = false;
};
+int qHash(FunctionsEditorModel::UniqueFunctionName fnName);
+
#endif // FUNCTIONSEDITORMODEL_H
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/sqliteextensioneditor.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/sqliteextensioneditor.cpp
index f8dd621..66e6682 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/sqliteextensioneditor.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/sqliteextensioneditor.cpp
@@ -123,6 +123,7 @@ void SqliteExtensionEditor::init()
connect(dbListModel, SIGNAL(dataChanged(QModelIndex,QModelIndex)), this, SLOT(updateModified()));
probingDb = DBLIST->createInMemDb(true);
+
if (!probingDb->openQuiet())
qWarning() << "Could not open in-memory dtabase for Extension manager window. Probing files will be impossible.";
@@ -308,6 +309,7 @@ void SqliteExtensionEditor::rollback()
if (model->isValidRowIndex(selectedBefore))
selectExtension(selectedBefore);
+ initStateForAll();
updateState();
}
@@ -337,7 +339,7 @@ void SqliteExtensionEditor::deleteExtension()
void SqliteExtensionEditor::updateState()
{
bool modified = model->isModified() || currentModified;
- bool valid = model->isValid() && validateCurrentExtension();
+ bool valid = model->isValid() && (getCurrentExtensionRow() == -1 || validateCurrentExtension());
actionMap[COMMIT]->setEnabled(modified && valid);
actionMap[ROLLBACK]->setEnabled(modified);
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.cpp
index 86f48bf..b42848a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.cpp
@@ -865,6 +865,9 @@ void TableWindow::changesSuccessfullyCommitted()
}
}
}
+
+ if (ui->tabWidget->currentIndex() == getDataTabIdx())
+ ui->dataView->refreshData();
}
void TableWindow::changesFailedToCommit(int errorCode, const QString& errorText)
@@ -1047,7 +1050,7 @@ bool TableWindow::validate(bool skipWarning)
QStringList nonStrictColumns;
for (SqliteCreateTable::Column* column : createTable->columns)
{
- if (DataType::isStrict(column->type->name))
+ if (DataType::isStrict(column->type ? column->type->name : QString()))
continue;
nonStrictColumns << column->name;
@@ -1310,7 +1313,7 @@ void TableWindow::importTable()
ImportDialog dialog(this);
dialog.setDbAndTable(db, table);
if (dialog.exec() == QDialog::Accepted && dataLoaded)
- ui->dataView->refreshData();
+ ui->dataView->refreshData(false);
}
void TableWindow::populateTable()
@@ -1318,7 +1321,7 @@ void TableWindow::populateTable()
PopulateDialog dialog(this);
dialog.setDbAndTable(db, table);
if (dialog.exec() == QDialog::Accepted && dataLoaded)
- ui->dataView->refreshData();
+ ui->dataView->refreshData(false);
}
void TableWindow::createSimilarTable()
@@ -1342,15 +1345,16 @@ void TableWindow::tabChanged(int newTab)
"Do you want to commit the structure, or do you want to go back to the structure tab?"),
tr("Go back to structure tab"), tr("Commit modifications and browse data."));
- ui->tabWidget->setCurrentIndex(0);
if (res == 1)
commitStructure(true);
+ else
+ focusStructureTab();
return;
}
if (!dataLoaded)
- ui->dataView->refreshData();
+ ui->dataView->refreshData(false);
}
}
@@ -1393,8 +1397,11 @@ void TableWindow::strictChanged()
{
for (SqliteCreateTable::Column* column : createTable->columns)
{
- column->type->precision = QVariant();
- column->type->scale = QVariant();
+ if (column->type)
+ {
+ column->type->precision = QVariant();
+ column->type->scale = QVariant();
+ }
}
}
@@ -1644,6 +1651,16 @@ void TableWindow::delColumn(const QString& columnName)
delColumn(colIdx);
}
+void TableWindow::focusStructureTab()
+{
+ ui->tabWidget->setCurrentIndex(getStructureTabIdx());
+}
+
+void TableWindow::focusDataTab()
+{
+ ui->tabWidget->setCurrentIndex(getDataTabIdx());
+}
+
void TableWindow::updateTabsOrder()
{
tabsMoving = true;
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.h b/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.h
index e71162d..dda317a 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.h
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/tablewindow.h
@@ -255,6 +255,8 @@ class GUI_API_EXPORT TableWindow : public MdiChild
void addColumn();
void editColumn(const QString& columnName);
void delColumn(const QString& columnName);
+ void focusStructureTab();
+ void focusDataTab();
signals:
void modifyStatusChanged();
diff --git a/SQLiteStudio3/guiSQLiteStudio/windows/viewwindow.cpp b/SQLiteStudio3/guiSQLiteStudio/windows/viewwindow.cpp
index 44025e5..73575c4 100644
--- a/SQLiteStudio3/guiSQLiteStudio/windows/viewwindow.cpp
+++ b/SQLiteStudio3/guiSQLiteStudio/windows/viewwindow.cpp
@@ -299,7 +299,7 @@ void ViewWindow::initView()
if (existingView)
{
dataModel->setDb(db);
- dataModel->setQuery(originalCreateView->select->detokenize());
+ dataModel->setQuery(originalCreateView->equivalentSelectTokens().detokenize());
dataModel->setDatabaseAndView(database, view);
ui->dbCombo->setDisabled(true);
}
@@ -619,7 +619,7 @@ void ViewWindow::tabChanged(int tabIdx)
"Do you want to commit the structure, or do you want to go back to the structure tab?"),
tr("Go back to structure tab"), tr("Commit modifications and browse data."));
- ui->tabWidget->setCurrentIndex(0);
+ ui->tabWidget->setCurrentIndex(CFG_UI.General.DataTabAsFirstInViews.get() ? 1 : 0);
if (res == 1)
commitView(true);
@@ -627,7 +627,7 @@ void ViewWindow::tabChanged(int tabIdx)
}
if (!dataLoaded)
- ui->dataView->refreshData();
+ ui->dataView->refreshData(false);
return;
}