Database disk image is malformed


#1

Hi!

I ran into a problem when running sqlcipher on Android.

I have an encrypted DB and a few activities that extract information from it.
The first activity takes information from one table to the list. By clicking on an item from the list I move the user to the second activity with the index of the selected item in the list.
The second activity extracts information from the DB (another table) as well to the list.

The problem is when I try to access the cursor.moveToFirst () function after the
Cursor cursor = db.rawQuery (query, null); line.

Full code:

String query = String.format(“select title,chapter_num from texts where topic_id = ‘%1$s’ order by chapter_num;”, index);
Cursor cursor = db.rawQuery(query, null);
cursor.moveToFirst();

I get the following error:
Fatal Exception: java.lang.RuntimeException: Unable to start activity ComponentInfo{com/com.Activity.ChapterIndex}: net.sqlcipher.database.SQLiteDatabaseCorruptException: database disk image is malformed
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2726)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2787)
at android.app.ActivityThread.-wrap12(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1504)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6247)
at java.lang.reflect.Method.invoke(Method.java)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:872)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:762)
Caused by net.sqlcipher.database.SQLiteDatabaseCorruptException: database disk image is malformed
at net.sqlcipher.database.SQLiteQuery.native_fill_window(SQLiteQuery.java)
at net.sqlcipher.database.SQLiteQuery.fillWindow(SQLiteQuery.java:79)
at net.sqlcipher.database.SQLiteCursor.fillWindow(SQLiteCursor.java:299)
at net.sqlcipher.database.SQLiteCursor.getCount(SQLiteCursor.java:280)
at net.sqlcipher.AbstractCursor.moveToPosition(AbstractCursor.java:178)
at net.sqlcipher.AbstractCursor.moveToFirst(AbstractCursor.java:222)
at android.database.CursorWrapper.moveToFirst(CursorWrapper.java:71)
at com.Utils.SQLiteDatabaseSingleton.getChaptersListByCursor(SQLiteDatabaseSingleton.java:71)
at com.Activity.ChapterIndex.onCreate(ChapterIndex.java:172)
at android.app.Activity.performCreate(Activity.java:6757)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1119)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2679)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2787)
at android.app.ActivityThread.-wrap12(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1504)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6247)
at java.lang.reflect.Method.invoke(Method.java)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:872)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:762)

The thing is, it happens on some devices (Xiaomi Redmi Note 4X, LG G5). For me there is no error.
More than that, we have already received what DB information. Why is there a problem with the second retrieval?

More information:

I use sqlcipher 3.5.7.
I added sqlcipher by add the following line to the build.gradle project file (I didn’t added so files or zip files to assets by myself… it’s ok?):
compile ‘net.zetetic:android-database-sqlcipher:3.5.7@aar’

Thanks!


#2

Hi @naory159

What does the formatted query look like prior to execution within the debugger? Are you able to retrieve the database file off device when it reports the corruption for further review?


#3

Hi @developernotes

The formated query looks like this:

select title,chapter_num from texts where topic_id = ‘6’ order by chapter_num;

The DB file deleted after the the exception thrown.


#4

Hello @naory159

Please provide a custom implementation of DatabaseErrorHandler (provided to the SQLiteDatabase::openDatabase function) to prevent the file from being deleted (it could possibly do nothing). Next, will you pull the database off the device and attempt to access the contents of the database with the known password? We look forward to hearing your results.