From 6b2480f10cc8b27d76e3d63ec5210b2e1dfd912a Mon Sep 17 00:00:00 2001 From: Simon Binder Date: Wed, 27 Nov 2019 18:54:05 +0100 Subject: [PATCH] moor_ffi: Performance improvements for sqlite3 on Android --- docs/content/en/docs/Other engines/vm.md | 27 ++++++++++++++++++++- moor_ffi/CHANGELOG.md | 4 ++++ moor_ffi/android/.gitignore | 3 +-- moor_ffi/android/cpp/CMakeLists.txt | 29 ++++++++++++++++++++++- moor_ffi/lib/src/bindings/bindings.dart | 7 ------ moor_ffi/lib/src/bindings/signatures.dart | 3 --- 6 files changed, 59 insertions(+), 14 deletions(-) diff --git a/docs/content/en/docs/Other engines/vm.md b/docs/content/en/docs/Other engines/vm.md index 0c4e5b04..9c94ba45 100644 --- a/docs/content/en/docs/Other engines/vm.md +++ b/docs/content/en/docs/Other engines/vm.md @@ -76,4 +76,29 @@ Note: If you haven't shipped a version with `moor_flutter` to your users yet, yo on `sqflite`. Instead, you can use `path_provider` which [works on Desktop](https://github.com/google/flutter-desktop-embedding/tree/master/plugins/flutter_plugins). Please be aware that `FlutterQueryExecutor.inDatabaseFolder` might yield a different folder than `path_provider` on Android. This can cause data loss if you've already shipped a version using -`moor_flutter`. In that case, using `getDatabasePath` from sqflite is the suggested solution. \ No newline at end of file +`moor_flutter`. In that case, using `getDatabasePath` from sqflite is the suggested solution. + +## Used compile options on Android + +Note: Android is the only platform where moor_ffi will compile sqlite. The sqlite3 library from the system +is used on all other platforms. The choosen options help reduce binary size by removing features not used by +moor. Important options are marked in bold. + +- We use the `-O3` performance option +- __SQLITE_DQS=0__: This will make sqlite not accept double-quoted strings (and instead parse them as identifiers). This matches + the behavior of moor and compiled queries +- __SQLITE_THREADSAFE=0__: Since the majority of Flutter apps only use one isolate, thread safety is turned off. Note that you + can still use the [isolate api]({{}}) for background operations. As long as all + database accesses happen from the same thread, there's no problem. +- SQLITE_DEFAULT_MEMSTATUS=0: The `sqlite3_status()` interfaces are not exposed by moor_ffi, so there's no point of having them. +- SQLITE_MAX_EXPR_DEPTH=0: Disables maximum depth when sqlite parses expressions, which can make the parser faster. +- `SQLITE_OMIT_AUTHORIZATION`, `SQLITE_OMIT_DECLTYPE`, __SQLITE_OMIT_DEPRECATED__, `SQLITE_OMIT_GET_TABLE`, `SQLITE_OMIT_LOAD_EXTENSION`, + `SQLITE_OMIT_PROGRESS_CALLBACK`, `SQLITE_OMIT_SHARED_CACHE`, `SQLITE_OMIT_TCL_VARIABLE`, `SQLITE_OMIT_TRACE`: Disables features not supported + by moor. +- `SQLITE_USE_ALLOCA`: Allocate temporary memory on the stack +- `SQLITE_UNTESTABLE`: Remove util functions that are only required to test sqlite3 +- `SQLITE_HAVE_ISNAN`: Use the `isnan` function from the system instead of the one shipped with sqlite3. +- `SQLITE_ENABLE_FTS5`: Enable the [fts5](https://www.sqlite.org/fts5.html) engine for full-text search. +- `SQLITE_ENABLE_JSON1`: Enable the [json1](https://www.sqlite.org/json1.html) extension for json support in sql query. + +For more details on sqlite compile options, see [their documentation](https://www.sqlite.org/compile.html). \ No newline at end of file diff --git a/moor_ffi/CHANGELOG.md b/moor_ffi/CHANGELOG.md index 62d67a9a..ab3398ca 100644 --- a/moor_ffi/CHANGELOG.md +++ b/moor_ffi/CHANGELOG.md @@ -1,3 +1,7 @@ +## unreleased + +- Better setup for compiling sqlite3 on Android + ## 0.2.0 - Remove the `background` flag from the moor apis provided by this package. Use the moor isolate api diff --git a/moor_ffi/android/.gitignore b/moor_ffi/android/.gitignore index 4a38248d..f49f1198 100644 --- a/moor_ffi/android/.gitignore +++ b/moor_ffi/android/.gitignore @@ -8,5 +8,4 @@ /captures .externalNativeBuild/ -cpp/sqlite* -sqlite_*.zip \ No newline at end of file +cpp/sqlite* \ No newline at end of file diff --git a/moor_ffi/android/cpp/CMakeLists.txt b/moor_ffi/android/cpp/CMakeLists.txt index 4e6a46d8..1d1452e6 100644 --- a/moor_ffi/android/cpp/CMakeLists.txt +++ b/moor_ffi/android/cpp/CMakeLists.txt @@ -1,4 +1,31 @@ cmake_minimum_required(VERSION 3.4.1) -project(sqlite3) +project( + moor_ffi_android + VERSION 3 + LANGUAGES C +) + +set(CMAKE_C_FLAGS "-O3") add_library(sqlite3 SHARED sqlite3.c) + +target_compile_definitions(sqlite3 PUBLIC + SQLITE_DQS=0 + SQLITE_THREADSAFE=0 + SQLITE_DEFAULT_MEMSTATUS=0 + SQLITE_MAX_EXPR_DEPTH=0 + SQLITE_OMIT_AUTHORIZATION + SQLITE_OMIT_DECLTYPE + SQLITE_OMIT_DEPRECATED + SQLITE_OMIT_GET_TABLE + SQLITE_OMIT_LOAD_EXTENSION + SQLITE_OMIT_PROGRESS_CALLBACK + SQLITE_OMIT_SHARED_CACHE + SQLITE_OMIT_TCL_VARIABLE + SQLITE_OMIT_TRACE + SQLITE_USE_ALLOCA + SQLITE_UNTESTABLE + SQLITE_HAVE_ISNAN + SQLITE_ENABLE_FTS5 + SQLITE_ENABLE_JSON1 +) \ No newline at end of file diff --git a/moor_ffi/lib/src/bindings/bindings.dart b/moor_ffi/lib/src/bindings/bindings.dart index 4bc66081..e25c0b3c 100644 --- a/moor_ffi/lib/src/bindings/bindings.dart +++ b/moor_ffi/lib/src/bindings/bindings.dart @@ -48,9 +48,6 @@ class _SQLiteBindings { Pointer Function(Pointer statement, int columnIndex) sqlite3_column_name; - Pointer Function(Pointer statement, int columnIndex) - sqlite3_column_decltype; - int Function(Pointer statement, int columnIndex) sqlite3_column_type; @@ -158,10 +155,6 @@ class _SQLiteBindings { .lookup>( 'sqlite3_column_name') .asFunction(); - sqlite3_column_decltype = sqlite - .lookup>( - 'sqlite3_column_decltype') - .asFunction(); sqlite3_column_type = sqlite .lookup>( 'sqlite3_column_type') diff --git a/moor_ffi/lib/src/bindings/signatures.dart b/moor_ffi/lib/src/bindings/signatures.dart index 6f0a0930..e3cd049b 100644 --- a/moor_ffi/lib/src/bindings/signatures.dart +++ b/moor_ffi/lib/src/bindings/signatures.dart @@ -47,9 +47,6 @@ typedef sqlite3_column_count_native_t = Int32 Function( typedef sqlite3_column_name_native_t = Pointer Function( Pointer statement, Int32 columnIndex); -typedef sqlite3_column_decltype_native_t = Pointer Function( - Pointer statement, Int32 columnIndex); - typedef sqlite3_column_type_native_t = Int32 Function( Pointer statement, Int32 columnIndex);