Android Tutorial Android database encryption with SQLCipher library

Status
Not open for further replies.
SQLCipher is an open source project that extends SQLite and adds full database encryption.
License: https://www.zetetic.net/sqlcipher/open-source/

B4A SQLCipher is a special subtype of SQL object. There is almost no need to change any code in order to switch from regular SQL to SQLCipher.

The only difference between SQL API and SQLCipher API is the Initialize method.
SQLCipher.Initialize expects two additional values: Password and a second parameter that is not used (it was used in the past).

Password is the database password. You can pass an empty string if there is no password. Note that it is not possible to change the password (or set a new password) to an existing database.

Code changes required to convert from SQL to SQLCipher
- Declare the SQL object as SQLCipher.
- Change the initialize code to:
B4X:
SQL1.Initialize(File.DirRootExternal, "1.db", True, DB_PASSWORD, "")

V1.70
V1.60
V1.50
  • Based on SQLCipher v3.59
  • Supports targetSdkVersion 26.
  • The icu.zip file is no longer required. You can delete it from the Files folder.
  • It is no longer required to disable the debugger virtual assets feature.
    Remove this line: #DebuggerForceStandardAssets: True
  • Old version: www.b4x.com/android/files/SQLCipher150.zip

Depends on: https://repo1.maven.org/maven2/net/...er/4.5.4/android-database-sqlcipher-4.5.4.aar
You should download and copy it to the additional libraries folder.
 

Attachments

  • SQLCipher.zip
    37.2 KB · Views: 426
Last edited:

tucano2000

Active Member
Licensed User
Longtime User
V1.40 is released with support for async SQL methods.

I am getting a issue after update 1.40. Now compiling is a sucessfull, but when run application in my phone, it crash and close.

In Debug mode you can see that the problem occurs when initialize sqlcipher.
log:


Logger connected to: samsung SM-A910F
--------- beginning of main
--------- beginning of system
** Activity (main) Create, isFirst = true **
** Activity (main) Resume **
** Activity (main) Pause, UserClosed = false **
** Activity (menuprincipal) Create, isFirst = true **
art/runtime/jni_internal.cc:497] JNI FatalError called: RegisterNatives failed for 'net/sqlcipher/database/SQLiteDatabase'; aborting...
art/runtime/runtime.cc:368] Runtime aborting...
art/runtime/runtime.cc:368]
Fatal signal 6 (SIGABRT), code -6 in tid 26095

Using B4A 7.01, copied and replaced 5 files to libraries folder and icudt46l.zip to assets folder.

I created a new separate project, containing only basic instructions for sqlcipher. The result was the same.
 
Last edited:

tucano2000

Active Member
Licensed User
Longtime User
Which device are you using? Which Android version?

Android 6.01 Samsung Galaxy A9 to before test.

Now another device Motorola XT1078 Android 6.0 log:

Logger connected to: motorola XT1078
--------- beginning of main
*** Service (starter) Create ***
** Service (starter) Start **
** Activity (main) Create, isFirst = true **
art/runtime/jni_internal.cc:497] JNI FatalError called: RegisterNatives failed for 'net/sqlcipher/database/SQLiteDatabase'; aborting...
art/runtime/runtime.cc:399] Runtime aborting...
art/runtime/runtime.cc:399] Aborting thread:
art/runtime/runtime.cc:399] "main" prio=5 tid=1 Native
art/runtime/runtime.cc:399] | group="" sCount=0 dsCount=0 obj=0x739ff2a0 self=0xb7e88590
art/runtime/runtime.cc:399] | sysTid=1392 nice=0 cgrp=default sched=0/0 handle=0xb6f88b34
art/runtime/runtime.cc:399] | state=R schedstat=( 0 0 0 ) utm=9 stm=6 core=0 HZ=100
art/runtime/runtime.cc:399] | stack=0xbe00d000-0xbe00f000 stackSize=8MB
art/runtime/runtime.cc:399] | held mutexes= "abort lock"
art/runtime/runtime.cc:399] native: #00 pc 00370c01 /system/lib/libart.so (_ZN3art15DumpNativeStackERNSt3__113basic_ostreamIcNS0_11char_traitsIcEEEEiPKcPNS_9ArtMethodEPv+160)
art/runtime/runtime.cc:399] native: #01 pc 0035054b /system/lib/libart.so (_ZNK3art6Thread4DumpERNSt3__113basic_ostreamIcNS1_11char_traitsIcEEEE+150)
art/runtime/runtime.cc:399] native: #02 pc 003333ab /system/lib/libart.so (_ZNK3art10AbortState10DumpThreadERNSt3__113basic_ostreamIcNS1_11char_traitsIcEEEEPNS_6ThreadE+26)
art/runtime/runtime.cc:399] native: #03 pc 00333643 /system/lib/libart.so (_ZN3art7Runtime5AbortEv+562)
art/runtime/runtime.cc:399] native: #04 pc 000f470b /system/lib/libart.so (_ZN3art10LogMessageD2Ev+2226)
art/runtime/runtime.cc:399] native: #05 pc 002704bd /system/lib/libart.so (_ZN3art3JNI10FatalErrorEP7_JNIEnvPKc+72)
art/runtime/runtime.cc:399] native: #06 pc 0000229f /system/lib/libnativehelper.so (jniRegisterNativeMethods+98)
art/runtime/runtime.cc:399] native: #07 pc 00006c27 /data/app/b4a.example-2/lib/arm/libdatabase_sqlcipher.so (???)
art/runtime/runtime.cc:399] native: #08 pc 00006c95 /data/app/b4a.example-2/lib/arm/libdatabase_sqlcipher.so (???)
art/runtime/runtime.cc:399] native: #09 pc 0025b16f /system/lib/libart.so (_ZN3art9JavaVMExt17LoadNativeLibraryEP7_JNIEnvRKNSt3__112basic_stringIcNS3_11char_traitsIcEENS3_9allocatorIcEEEEP8_jobjectPS9_+1238)
art/runtime/runtime.cc:399] native: #10 pc 002d1427 /system/lib/libart.so (_ZN3artL18Runtime_nativeLoadEP7_JNIEnvP7_jclassP8_jstringP8_jobjectS5_+194)
art/runtime/runtime.cc:399] native: #11 pc 0021bb65 /system/framework/arm/boot.oat (???)
art/runtime/runtime.cc:399] at java.lang.Runtime.nativeLoad(Native method)
art/runtime/runtime.cc:399] at java.lang.Runtime.doLoad(Runtime.java:435)
art/runtime/runtime.cc:399] - locked <0x0061aed3> (a java.lang.Runtime)
art/runtime/runtime.cc:399] at java.lang.Runtime.loadLibrary(Runtime.java:370)
art/runtime/runtime.cc:399] at java.lang.System.loadLibrary(System.java:1076)
art/runtime/runtime.cc:399] at net.sqlcipher.database.SQLiteDatabase.loadLibs(SQLiteDatabase.java:144)
art/runtime/runtime.cc:399] at net.sqlcipher.database.SQLiteDatabase.loadLibs(SQLiteDatabase.java:137)
art/runtime/runtime.cc:399] at anyhwheresoftware.b4a.objects.sqlcipher.SQLCipher.Initialize(SQLCipher.java:51)
art/runtime/runtime.cc:399] at b4a.example.main._activity_create(main.java:334)
art/runtime/runtime.cc:399] at java.lang.reflect.Method.invoke!(Native method)
art/runtime/runtime.cc:399] at anywheresoftware.b4a.BA.raiseEvent2(BA.java:186)
art/runtime/runtime.cc:399] at b4a.example.main.afterFirstLayout(main.java:102)
art/runtime/runtime.cc:399] at b4a.example.main.access$000(main.java:17)
art/runtime/runtime.cc:399] at b4a.example.main$WaitForLayout.run(main.java:80)
art/runtime/runtime.cc:399] at android.os.Handler.handleCallback(Handler.java:746)
art/runtime/runtime.cc:399] at android.os.Handler.dispatchMessage(Handler.java:95)
art/runtime/runtime.cc:399] at android.os.Looper.loop(Looper.java:148)
art/runtime/runtime.cc:399] at android.app.ActivityThread.main(ActivityThread.java:5443)
art/runtime/runtime.cc:399] at java.lang.reflect.Method.invoke!(Native method)
art/runtime/runtime.cc:399] at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:728)
art/runtime/runtime.cc:399] at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
art/runtime/runtime.cc:399] Pending exception java.lang.NoSuchMethodError: no static or non-static method "Lnet/sqlcipher/database/SQLiteDatabase;.native_rekey([C)V"
art/runtime/runtime.cc:399] at java.lang.String java.lang.Runtime.nativeLoad(java.lang.String, java.lang.ClassLoader, java.lang.String) (Runtime.java:-2)
art/runtime/runtime.cc:399] at java.lang.String java.lang.Runtime.doLoad(java.lang.String, java.lang.ClassLoader) (Runtime.java:435)
art/runtime/runtime.cc:399] at void java.lang.Runtime.loadLibrary(java.lang.String, java.lang.ClassLoader) (Runtime.java:370)
art/runtime/runtime.cc:399] at void java.lang.System.loadLibrary(java.lang.String) (System.java:1076)
art/runtime/runtime.cc:399] at void net.sqlcipher.database.SQLiteDatabase.loadLibs(android.content.Context, java.io.File) (SQLiteDatabase.java:144)
art/runtime/runtime.cc:399] at void net.sqlcipher.database.SQLiteDatabase.loadLibs(android.content.Context) (SQLiteDatabase.java:137)
art/runtime/runtime.cc:399] at void anyhwheresoftware.b4a.objects.sqlcipher.SQLCipher.Initialize(java.lang.String, java.lang.String, boolean, java.lang.String, java.lang.String) (SQLCipher.java:51)
art/runtime/runtime.cc:399] at java.lang.String b4a.example.main._activity_create(boolean) (main.java:334)
art/runtime/runtime.cc:399] at java.lang.Object java.lang.reflect.Method.invoke!(java.lang.Object, java.lang.Object[]) (Method.java:-2)
art/runtime/runtime.cc:399] at java.lang.Object anywheresoftware.b4a.BA.raiseEvent2(java.lang.Object, boolean, java.lang.String, boolean, java.lang.Object[]) (BA.java:186)
art/runtime/runtime.cc:399] at void b4a.example.main.afterFirstLayout() (main.java:102)
art/runtime/runtime.cc:399] at void b4a.example.main.access$000(b4a.example.main) (main.java:17)
art/runtime/runtime.cc:399] at void b4a.example.main$WaitForLayout.run() (main.java:80)
art/runtime/runtime.cc:399] at void android.os.Handler.handleCallback(android.os.Message) (Handler.java:746)
art/runtime/runtime.cc:399] at void android.os.Handler.dispatchMessage(android.os.Message) (Handler.java:95)
art/runtime/runtime.cc:399] at void android.os.Looper.loop() (Looper.java:148)
art/runtime/runtime.cc:399] at void android.app.ActivityThread.main(java.lang.String[]) (ActivityThread.java:5443)
art/runtime/runtime.cc:399] at java.lang.Object java.lang.reflect.Method.invoke!(java.lang.Object, java.lang.Object[]) (Method.java:-2)
art/runtime/runtime.cc:399] at void com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run() (ZygoteInit.java:728)
art/runtime/runtime.cc:399] at void com.android.internal.os.ZygoteInit.main(java.lang.String[]) (ZygoteInit.java:618)
art/runtime/runtime.cc:399] Dumping all threads without appropriate locks held: thread list lock mutator lock
art/runtime/runtime.cc:399] All threads:
art/runtime/runtime.cc:399] DALVIK THREADS (13):
art/runtime/runtime.cc:399] "main" prio=5 tid=1 Runnable
art/runtime/runtime.cc:399] | group="" sCount=0 dsCount=0 obj=0x739ff2a0 self=0xb7e88590
art/runtime/runtime.cc:399] | sysTid=1392 nice=0 cgrp=default sched=0/0 handle=0xb6f88b34
art/runtime/runtime.cc:399] | state=R schedstat=( 0 0 0 ) utm=11 stm=8 core=0 HZ=100
art/runtime/runtime.cc:399] | stack=0xbe00d000-0xbe00f000 stackSize=8MB
art/runtime/runtime.cc:399] | held mutexes= "abort lock" "mutator lock"(shared held)
art/runtime/runtime.cc:399] native: #00 pc 00370c01 /system/lib/libart.so (_ZN3art15DumpNativeStackERNSt3__113basic_ostreamIcNS0_11char_traitsIcEEEEiPKcPNS_9ArtMethodEPv+160)
art/runtime/runtime.cc:399] native: #01 pc 0035054b /system/lib/libart.so (_ZNK3art6Thread4DumpERNSt3__113basic_ostreamIcNS1_11char_traitsIcEEEE+150)
art/runtime/runtime.cc:399] native: #02 pc 0035a1b3 /system/lib/libart.so (_ZN3art14DumpCheckpoint3RunEPNS_6ThreadE+442)
art/runtime/runtime.cc:399] native: #03 pc 0035ad5f /system/lib/libart.so (_ZN3art10ThreadList13RunCheckpointEPNS_7ClosureE+210)
art/runtime/runtime.cc:399] native: #04 pc 0035b29f /system/lib/libart.so (_ZN3art10ThreadList4DumpERNSt3__113basic_ostreamIcNS1_11char_traitsIcEEEE+142)
 

Erel

B4X founder
Staff member
Licensed User
Longtime User
Works fine here. These are the library files:
SS-2017-06-21_12.25.01.png


Are they the same as yours?
 

tucano2000

Active Member
Licensed User
Longtime User
sqlcipher_native.jar is with different size and date. anothers files are with different date.

But I downloaded the link that was removed from post 142.

The link that was in the browser history when I downloaded it was this.

https://www.b4x.com/android/files/SQLCipher.zip

There is another correct link for 1.40 ?
 

Attachments

  • sqlcipher.png
    sqlcipher.png
    12.6 KB · Views: 541
Last edited:

Rusty

Well-Known Member
Licensed User
Longtime User
I have updated my v1.3 to v1.4 and now my app will not run.
I'm getting the following in my unfiltered logs:
Added shared lib /data/app-lib/b4a.example-1/libdatabase_sqlcipher.so 0x43c4d990
JNI_OnLoad called
JNI_OnLoad register methods
ERROR: couldn't find native method
Requested: Lnet/sqlcipher/database/SQLiteDatabase;.native_rekey:([C)V
JNI posting fatal error: RegisterNatives failed for 'net/sqlcipher/database/SQLiteDatabase'; aborting...
"main" prio=5 tid=1 NATIVE
| group="main" sCount=0 dsCount=0 obj=0x437c1360 self=0x437af020
| sysTid=30673 nice=0 sched=0/0 cgrp=apps handle=1073954880
| state=R schedstat=( 2040976273 393218579 3338 ) utm=155 stm=49 core=1
#00 pc 00113498 /system/lib/libdvm.so (dvmDumpNativeStack(DebugOutputTarget const*, int)+72)
#01 pc 000f008b /system/lib/libdvm.so (dvmDumpThreadEx(DebugOutputTarget const*, Thread*, bool)+1099)
#02 pc 000f02ef /system/lib/libdvm.so (dvmDumpThread(Thread*, bool)+63)
#03 pc 000d1e0c /system/lib/libdvm.so
#04 pc 00001c89 /system/lib/libnativehelper.so (jniRegisterNativeMethods+153)
#05 pc 001a6ae9 /system/lib/libhoudini.so.4.0.8.45720
at java.lang.Runtime.nativeLoad(Native Method)
at java.lang.Runtime.doLoad(Runtime.java:421)
at java.lang.Runtime.loadLibrary(Runtime.java:362)
at java.lang.System.loadLibrary(System.java:526)
at net.sqlcipher.database.SQLiteDatabase.loadLibs(SQLiteDatabase.java:144)
at net.sqlcipher.database.SQLiteDatabase.loadLibs(SQLiteDatabase.java:137)
at anyhwheresoftware.b4a.objects.sqlcipher.SQLCipher.Initialize(SQLCipher.java:51)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at anywheresoftware.b4a.shell.Shell.runVoidMethod(Shell.java:755)
at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:345)
at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:249)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:139)
at b4a.example.main.afterFirstLayout(main.java:102)
at b4a.example.main.access$000(main.java:17)
at b4a.example.main$WaitForLayout.run(main.java:80)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:149)
at android.app.ActivityThread.main(ActivityThread.java:5257)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:794)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:610)
at dalvik.system.NativeStart.main(Native Method)
VM aborting
Fatal signal 6 (SIGABRT) at 0x000077d1 (code=-6), thread 30673 (b4a.example)
This occurs on the first initialization of the first SQLCipher database I try to open.
Any ideas are greatly appreciated.
Rusty
 

Rusty

Well-Known Member
Licensed User
Longtime User
Hi Erel,
Yes, it does work on my device. (BTW, BridgeCLI is cool and I agree, it would be great to "mass install" an app on all discovered devices. It would make my install/burn in of devices easier I frequently install/burn in 100 tablets at a time :) )
My PC SQLCipher creates my database and is using
Version 9
03.29.16
I'm wondering if this version isn't compatible with 1.4?
Regards,
Rusty
 

SMOOTSARA

Active Member
Licensed User
Longtime User
Hey guys :)

I used this library to protect data

Before the encryption, the database size was 104 MB, but after the encryption 98.2 MB.
(The volume of the database was reduced to 6 MB).:D:D

But

After the release of the program, we see that the APK file size has changed from 22.5 MB to 104 MB !!!!!! o_Oo_Oo_O

If after the encryption the volume of the database is reduced 6 MB, how is the program size larger(22.5 MB ==> 104 MB)? :eek::eek::eek:
Could you describe this phenomenon to me?
 
Status
Not open for further replies.
Top