Skip to content
Open
30 changes: 27 additions & 3 deletions demos/android/MASVS-STORAGE/MASTG-DEMO-0068/MASTG-DEMO-0068.md

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The DEMO must follow the content guidelines (https://mas.owasp.org/contributing/writing-content/mastg-demo.instructions).

For example, the "Evaluation" section should explain each relevant line of the output that is used as an evidence to give a FAIL to the test.

Original file line number Diff line number Diff line change
@@ -1,9 +1,33 @@
---
platform: android
title: Reserved for MASWE-0006 - Unencrypted SQLite Storage (Alternative Demo)
title: Sensitive Data in Unencrypted SQLite
id: MASTG-DEMO-0068
code: [kotlin]
test: MASTG-TEST-0304
Comment thread
macik09 marked this conversation as resolved.
status: placeholder
note: This placeholder reserves the ID for a potential alternative or expanded demo related to unencrypted SQLite storage, linked to the MASTG-TEST-0304 test case.
status: new
---

### Sample

The snippet below shows sample code that uses the default SQLite API (`context.openOrCreateDatabase`) to store sensitive data, including PII and an access token, without any encryption.

{{ MastgTest.kt }}

### Steps

1. Install the application on a test device.
2. Open the app and exercise it to trigger the database creation and data insertion.
3. Execute the analysis script **`run.sh`**.
4. The script pulls the database file (`PrivateUnencryptedData.db`) and queries its content.
Comment thread
macik09 marked this conversation as resolved.
Outdated

{{ run.sh }}

### Observation

The `output.txt` file contains the extracted content from the `Users` table, showing the sensitive PII (email address) and the access token stored in **plaintext**.
Comment thread
macik09 marked this conversation as resolved.
Outdated

{{ output.txt }}

### Evaluation

This test fails because the application stores highly sensitive data (Access Token and PII like the user's email address) using the standard SQLite API. By default, SQLite stores data in an unencrypted file within the app's private sandbox, violating the **MASVS-STORAGE** requirement (MASWE-0006). This data is trivially accessible if an attacker achieves privileged access to the device (e.g., via root).
Comment thread
macik09 marked this conversation as resolved.
Outdated
42 changes: 42 additions & 0 deletions demos/android/MASVS-STORAGE/MASTG-DEMO-0068/MastgTest.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
package org.owasp.mastestapp

import android.content.Context
import android.database.sqlite.SQLiteDatabase
import android.util.Log

class MastgTest (private val context: Context){


fun writeSensitiveDataToUnencryptedSQLite() {
val username = "demoUser_sqlite"
val userEmail = "john.doe@maswe-0006.com"
val accessToken = "MASTG_ACCESS_TOKEN_B4C8D2F0E7A"
Comment thread
macik09 marked this conversation as resolved.
Outdated
val dbName = "PrivateUnencryptedData"

try {
val db: SQLiteDatabase = context.openOrCreateDatabase(
dbName,
Context.MODE_PRIVATE,
null
)

db.execSQL("CREATE TABLE IF NOT EXISTS Users(Username VARCHAR, Email VARCHAR, Token VARCHAR);")


db.execSQL("DELETE FROM Users;")

db.execSQL("INSERT INTO Users VALUES('$username', '$userEmail', '$accessToken');")

db.close()
Log.i("MASTG-SQLITE", "Data written to unencrypted database: $dbName. Ready for ADB extraction.")

} catch (e: Exception) {
Log.e("MASTG-SQLITE", "Error writing data to SQLite: ${e.message}")
}
}

fun mastgTest(): String {
writeSensitiveDataToUnencryptedSQLite()
return "SQLite Demo Complete. Database 'PrivateUnencryptedData' created with PII and Token."
}
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This Java file does not seem to be the Java file resulting from decompiling the DEMO app. As commented previously, follow the DEMO guidelines (https://mas.owasp.org/contributing/writing-content/mastg-demo.instructions/) to provide these files accordingly.

Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package org.owasp.mastestapp;

import android.content.Context;
import android.util.Log;
import kotlin.Metadata;
import kotlin.jvm.internal.Intrinsics;

/* compiled from: MastgTest.kt */
@Metadata(d1 = {"\u0000\u0018\n\u0002\u0018\u0002\n\u0002\u0010\u0000\n\u0000\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0010\u000e\n\u0000\b\u0007\u0018\u00002\u00020\u0001B\u000f\u0012\u0006\u0010\u0002\u001a\u00020\u0003¢\u0006\u0004\b\u0004\u0010\u0005J\u0006\u0010\u0006\u001a\u00020\u0007R\u000e\u0010\u0002\u001a\u00020\u0003X\u0082\u0004¢\u0006\u0002\n\u0000¨\u0006\b"}, d2 = {"Lorg/owasp/mastestapp/MastgTest;", "", "context", "Landroid/content/Context;", "<init>", "(Landroid/content/Context;)V", "mastgTest", "", "app_debug"}, k = 1, mv = {2, 0, 0}, xi = 48)
/* loaded from: classes3.dex */
public final class MastgTest {
public static final int $stable = 8;
private final Context context;

public MastgTest(Context context) {
Intrinsics.checkNotNullParameter(context, "context");
this.context = context;
}

public final String mastgTest() throws Exception {
DemoResults r = new DemoResults("0000");
try {
Log.d("MASTG-TEST", "Hello from the OWASP MASTG Test app.");
r.add(Status.PASS, "The app implemented a demo which passed the test with the following value: 'Hello from the OWASP MASTG Test app.'");
r.add(Status.FAIL, "The app implemented a demo which failed the test.");
throw new Exception("Example exception: Method not implemented.");
} catch (Exception e) {
r.add(Status.ERROR, e.toString());
return r.toJson();
}
}
}
2 changes: 2 additions & 0 deletions demos/android/MASVS-STORAGE/MASTG-DEMO-0068/output.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
--- Users Table Content ---
demoUser_sqlite|john.doe@maswe-0006.com|MASTG_ACCESS_TOKEN_B4C8D2F0E7A
27 changes: 27 additions & 0 deletions demos/android/MASVS-STORAGE/MASTG-DEMO-0068/run.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#!/bin/bash
Comment thread
macik09 marked this conversation as resolved.

PACKAGE="org.owasp.mastestapp"
DB_NAME="PrivateUnencryptedData"
DB_PATH="/data/data/$PACKAGE/databases/$DB_NAME"
SDCARD_PULL_PATH="/sdcard/$DB_NAME.db"
OUTPUT_DB_FILE="${DB_NAME}.db"
OUTPUT_TXT_FILE="output.txt"

# Step 1: Database Extraction
adb shell "run-as $PACKAGE cp databases/$DB_NAME $SDCARD_PULL_PATH" 2>/dev/null

# Attempt to copy via root access using here document
adb shell <<EOF
su
cp $DB_PATH $SDCARD_PULL_PATH
exit
EOF
Comment thread
macik09 marked this conversation as resolved.
Outdated

# Pull the file to the host machine
adb pull "$SDCARD_PULL_PATH" .

echo "--- Users Table Content ---" > $OUTPUT_TXT_FILE
sqlite3 "$OUTPUT_DB_FILE" "SELECT * FROM Users;" >> $OUTPUT_TXT_FILE

adb shell "rm $SDCARD_PULL_PATH" 2>/dev/null
rm $OUTPUT_DB_FILE 2>/dev/null
Comment thread
macik09 marked this conversation as resolved.