Skip to content
Permalink
Browse files
adopt 'new' spatialite initialization scheme via thin wrapper around …
…sqlite3_open and sqlite3_close (fixes #12771)
  • Loading branch information
jef-n committed May 26, 2015
1 parent 47cb75d commit 252aaab89e5701d1d7c0ec147ce02c8865ffa452
@@ -214,6 +214,13 @@ ENDIF (WITH_POSTGRESQL)

FIND_PACKAGE(SPATIALITE REQUIRED)

IF(SPATIALITE_VERSION_GE_4_0_0)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DSPATIALITE_VERSION_GE_4_0_0")
ENDIF(SPATIALITE_VERSION_GE_4_0_0)
IF(SPATIALITE_VERSION_G_4_1_1)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DSPATIALITE_VERSION_G_4_1_1")
ENDIF(SPATIALITE_VERSION_G_4_1_1)

IF (NOT PROJ_FOUND OR NOT GEOS_FOUND OR NOT GDAL_FOUND)
MESSAGE (SEND_ERROR "Some dependencies were not found!")
ENDIF (NOT PROJ_FOUND OR NOT GEOS_FOUND OR NOT GDAL_FOUND)
@@ -29,6 +29,7 @@
#include "prepare_protocol.h"
#include "util.h"
#include "sqlitecompat.h"
#include "spatialite.h"

#include "pythread.h"

@@ -81,7 +82,6 @@ int pysqlite_connection_init(pysqlite_Connection* self, PyObject* args, PyObject
}

self->initialized = 1;
spatialite_init(0);
self->begin_statement = NULL;

self->statement_cache = NULL;
@@ -106,7 +106,15 @@ int pysqlite_connection_init(pysqlite_Connection* self, PyObject* args, PyObject
}

Py_BEGIN_ALLOW_THREADS
#if defined(SPATIALITE_VERSION_GE_4_0_0)
self->slconn = spatialite_alloc_connection();
#else
spatialite_init( 0 );
#endif
rc = sqlite3_open(PyString_AsString(database_utf8), &self->db);
#if defined(SPATIALITE_VERSION_GE_4_0_0)
spatialite_init_ex( self->db, self->slconn, 0 );
#endif
Py_END_ALLOW_THREADS

Py_DECREF(database_utf8);
@@ -272,6 +280,7 @@ void pysqlite_connection_dealloc(pysqlite_Connection* self)
if (self->db) {
Py_BEGIN_ALLOW_THREADS
sqlite3_close(self->db);
spatialite_cleanup_ex( self->slconn );
Py_END_ALLOW_THREADS
} else if (self->apsw_connection) {
ret = PyObject_CallMethod(self->apsw_connection, "close", "");
@@ -372,6 +381,7 @@ PyObject* pysqlite_connection_close(pysqlite_Connection* self, PyObject* args)
} else {
Py_BEGIN_ALLOW_THREADS
rc = sqlite3_close(self->db);
spatialite_cleanup_ex( self->slconn );
Py_END_ALLOW_THREADS

if (rc != SQLITE_OK) {
@@ -33,12 +33,11 @@
#include "sqlite3.h"
#include "spatialite.h"

// int spatialite_init(int verbose);

typedef struct
{
PyObject_HEAD
sqlite3* db;
void *slconn;

/* 1 if we are currently within a transaction, i. e. if a BEGIN has been
* issued */
@@ -14,14 +14,11 @@
***************************************************************************/

#include "qgsosmdatabase.h"

#include <spatialite.h>

#include "qgsslconnect.h"
#include "qgsgeometry.h"
#include "qgslogger.h"



QgsOSMDatabase::QgsOSMDatabase( const QString& dbFileName )
: mDbFileName( dbFileName )
, mDatabase( 0 )
@@ -32,7 +29,6 @@ QgsOSMDatabase::QgsOSMDatabase( const QString& dbFileName )
, mStmtWayNodePoints( 0 )
, mStmtWayTags( 0 )
{

}

QgsOSMDatabase::~QgsOSMDatabase()
@@ -49,11 +45,8 @@ bool QgsOSMDatabase::isOpen() const

bool QgsOSMDatabase::open()
{
// load spatialite extension
spatialite_init( 0 );

// open database
int res = sqlite3_open_v2( mDbFileName.toUtf8().data(), &mDatabase, SQLITE_OPEN_READWRITE, 0 );
int res = QgsSLConnect::sqlite3_open_v2( mDbFileName.toUtf8().data(), &mDatabase, SQLITE_OPEN_READWRITE, 0 );
if ( res != SQLITE_OK )
{
mError = QString( "Failed to open database [%1]: %2" ).arg( res ).arg( mDbFileName );
@@ -93,7 +86,7 @@ bool QgsOSMDatabase::close()
Q_ASSERT( mStmtNode == 0 );

// close database
if ( sqlite3_close( mDatabase ) != SQLITE_OK )
if ( QgsSLConnect::sqlite3_close( mDatabase ) != SQLITE_OK )
{
//mError = ( char * ) "Closing SQLite3 database failed.";
//return false;
@@ -14,8 +14,7 @@
***************************************************************************/

#include "qgsosmimport.h"

#include <spatialite.h>
#include "qgsslconnect.h"

#include <QStringList>
#include <QXmlStreamReader>
@@ -57,9 +56,6 @@ bool QgsOSMXmlImport::import()
}
}

// load spatialite extension
spatialite_init( 0 );

if ( !createDatabase() )
{
// mError is set in createDatabase()
@@ -137,7 +133,7 @@ bool QgsOSMXmlImport::createDatabase()
{
char **results;
int rows, columns;
if ( sqlite3_open_v2( mDbFileName.toUtf8().data(), &mDatabase, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, 0 ) != SQLITE_OK )
if ( QgsSLConnect::sqlite3_open_v2( mDbFileName.toUtf8().data(), &mDatabase, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, 0 ) != SQLITE_OK )
return false;

bool above41 = false;
@@ -238,7 +234,7 @@ bool QgsOSMXmlImport::closeDatabase()

Q_ASSERT( mStmtInsertNode == 0 );

sqlite3_close( mDatabase );
QgsSLConnect::sqlite3_close( mDatabase );
mDatabase = 0;
return true;
}
@@ -24,10 +24,11 @@
#include "qgsapplication.h"
#include "qgsproviderregistry.h"
#include "qgisapp.h" // <- for theme icons
#include <qgsvectorlayer.h>
#include <qgsmaplayerregistry.h>
#include "qgsvectorlayer.h"
#include "qgsmaplayerregistry.h"
#include "qgscoordinatereferencesystem.h"
#include "qgsgenericprojectionselector.h"
#include "qgsslconnect.h"

#include "qgslogger.h"

@@ -196,14 +197,11 @@ void QgsNewSpatialiteLayerDialog::on_pbnFindSRID_clicked()
// to build filter for projection selector
sqlite3 *db = 0;
bool status = true;
if ( !db )
int rc = sqlite3_open_v2( mDatabaseComboBox->currentText().toUtf8(), &db, SQLITE_OPEN_READONLY, NULL );
if ( rc != SQLITE_OK )
{
int rc = sqlite3_open_v2( mDatabaseComboBox->currentText().toUtf8(), &db, SQLITE_OPEN_READONLY, NULL );
if ( rc != SQLITE_OK )
{
QMessageBox::warning( this, tr( "SpatiaLite Database" ), tr( "Unable to open the database" ) );
return;
}
QMessageBox::warning( this, tr( "SpatiaLite Database" ), tr( "Unable to open the database" ) );
return;
}

// load up the srid table
@@ -213,7 +211,7 @@ void QgsNewSpatialiteLayerDialog::on_pbnFindSRID_clicked()

QSet<QString> myCRSs;

int rc = sqlite3_prepare( db, sql.toUtf8(), sql.toUtf8().length(), &ppStmt, &pzTail );
rc = sqlite3_prepare( db, sql.toUtf8(), sql.toUtf8().length(), &ppStmt, &pzTail );
// XXX Need to free memory from the error msg if one is set
if ( rc == SQLITE_OK )
{
@@ -381,10 +379,8 @@ bool QgsNewSpatialiteLayerDialog::apply()
.arg( quotedValue( leGeometryColumn->text() ) );
QgsDebugMsg( sqlCreateIndex ); // OK

spatialite_init( 0 );

sqlite3 *db;
int rc = sqlite3_open( mDatabaseComboBox->currentText().toUtf8(), &db );
int rc = QgsSLConnect::sqlite3_open( mDatabaseComboBox->currentText().toUtf8(), &db );
if ( rc != SQLITE_OK )
{
QMessageBox::warning( this,
@@ -447,6 +443,8 @@ bool QgsNewSpatialiteLayerDialog::apply()
}
}
}

QgsSLConnect::sqlite3_close( db );
}

return false;
@@ -185,6 +185,7 @@ SET(QGIS_CORE_SRCS
qgsvectorlayerundocommand.cpp
qgsvectorsimplifymethod.cpp
qgsxmlutils.cpp
qgsslconnect.cpp

composer/qgsaddremoveitemcommand.cpp
composer/qgsaddremovemultiframecommand.cpp
@@ -29,6 +29,7 @@
#include "qgsvectordataprovider.h"
#include "qgsvectorlayereditbuffer.h"
#include "qgsvectorlayerjoinbuffer.h"
#include "qgsslconnect.h"

#include <QDir>
#include <QDomDocument>
@@ -74,9 +75,8 @@ bool QgsOfflineEditing::convertToOfflineProject( const QString& offlineDataPath,
QString dbPath = QDir( offlineDataPath ).absoluteFilePath( offlineDbFile );
if ( createSpatialiteDB( dbPath ) )
{
spatialite_init( 0 );
sqlite3* db;
int rc = sqlite3_open( dbPath.toUtf8().constData(), &db );
int rc = QgsSLConnect::sqlite3_open( dbPath.toUtf8().constData(), &db );
if ( rc != SQLITE_OK )
{
showWarning( tr( "Could not open the spatialite database" ) );
@@ -156,7 +156,7 @@ bool QgsOfflineEditing::convertToOfflineProject( const QString& offlineDataPath,

emit progressStopped();

sqlite3_close( db );
QgsSLConnect::sqlite3_close( db );

// save offline project
QString projectTitle = QgsProject::instance()->title();
@@ -380,8 +380,7 @@ bool QgsOfflineEditing::createSpatialiteDB( const QString& offlineDbPath )

// creating/opening the new database
QString dbPath = newDb.fileName();
spatialite_init( 0 );
ret = sqlite3_open_v2( dbPath.toUtf8().constData(), &sqlite_handle, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL );
ret = QgsSLConnect::sqlite3_open_v2( dbPath.toUtf8().constData(), &sqlite_handle, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL );
if ( ret )
{
// an error occurred
@@ -397,13 +396,13 @@ bool QgsOfflineEditing::createSpatialiteDB( const QString& offlineDbPath )
{
showWarning( tr( "Unable to activate FOREIGN_KEY constraints" ) );
sqlite3_free( errMsg );
sqlite3_close( sqlite_handle );
QgsSLConnect::sqlite3_close( sqlite_handle );
return false;
}
initializeSpatialMetadata( sqlite_handle );

// all done: closing the DB connection
sqlite3_close( sqlite_handle );
QgsSLConnect::sqlite3_close( sqlite_handle );

return true;
}

2 comments on commit 252aaab

@slarosa

This comment has been minimized.

Copy link
Member

@slarosa slarosa replied May 27, 2015

Hi @jef-n,
I am not sure whether it is a problem with my machine, but I am getting an error on building the master version and it seems to be related to this changes:

[  1%] Building CXX object src/core/CMakeFiles/qgis_core.dir/qgsslconnect.cpp.o
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp: In static member function ‘static int QgsSLConnect::sqlite3_open(const char*, sqlite3**)’:
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:28:44: error: ‘spatialite_alloc_connection’ was not declared in this scope
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:38:40: error: ‘spatialite_init_ex’ was not declared in this scope
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp: In static member function ‘static int QgsSLConnect::sqlite3_close(sqlite3*)’:
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:52:48: error: ‘spatialite_cleanup_ex’ was not declared in this scope
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp: In static member function ‘static int QgsSLConnect::sqlite3_open_v2(const char*, sqlite3**, int, const char*)’:
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:61:44: error: ‘spatialite_alloc_connection’ was not declared in this scope
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:71:40: error: ‘spatialite_init_ex’ was not declared in this scope
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp: In static member function ‘static int QgsSLConnect::sqlite3_close_v2(sqlite3*)’:
/home/sam/pacchetti_gis/QGIS/src/core/qgsslconnect.cpp:85:48: error: ‘spatialite_cleanup_ex’ was not declared in this scope
make[2]: *** [src/core/CMakeFiles/qgis_core.dir/qgsslconnect.cpp.o] Error 1
make[1]: *** [src/core/CMakeFiles/qgis_core.dir/all] Error 2
make: *** [all] Error 2

This is happening on Debian Wheezy.with SL4.0.0.
Thanks.

@slarosa

This comment has been minimized.

Copy link
Member

@slarosa slarosa replied May 27, 2015

@jef-n thanks for the commit d4b72a2, that has resolved the problem for me although I had to change the line 21 in qgsslconnect.cpp as well.

Please sign in to comment.