Migrate from SQLite and ciphertext blobs to SQLCipher + KeyStore

This commit is contained in:
Moxie Marlinspike
2018-01-24 19:17:44 -08:00
parent d1819b6361
commit f36b296e2e
134 changed files with 3633 additions and 3544 deletions

View File

@@ -1,4 +1,4 @@
/**
/*
* Copyright (C) 2011 Whisper Systems
*
* This program is free software: you can redistribute it and/or modify
@@ -16,6 +16,7 @@
*/
package org.thoughtcrime.securesms.notifications;
import android.annotation.SuppressLint;
import android.app.AlarmManager;
import android.app.NotificationManager;
import android.app.PendingIntent;
@@ -32,14 +33,12 @@ import android.os.AsyncTask;
import android.os.Build;
import android.service.notification.StatusBarNotification;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.app.NotificationManagerCompat;
import android.text.TextUtils;
import android.util.Log;
import org.thoughtcrime.securesms.ConversationActivity;
import org.thoughtcrime.securesms.R;
import org.thoughtcrime.securesms.crypto.MasterSecret;
import org.thoughtcrime.securesms.database.DatabaseFactory;
import org.thoughtcrime.securesms.database.MessagingDatabase.MarkedMessageInfo;
import org.thoughtcrime.securesms.database.MmsSmsDatabase;
@@ -184,28 +183,25 @@ public class MessageNotifier {
}
}
public static void updateNotification(@NonNull Context context, @Nullable MasterSecret masterSecret) {
public static void updateNotification(@NonNull Context context) {
if (!TextSecurePreferences.isNotificationsEnabled(context)) {
return;
}
updateNotification(context, masterSecret, false, 0);
updateNotification(context, false, 0);
}
public static void updateNotification(@NonNull Context context,
@Nullable MasterSecret masterSecret,
long threadId)
public static void updateNotification(@NonNull Context context, long threadId)
{
if (System.currentTimeMillis() - lastDesktopActivityTimestamp < DESKTOP_ACTIVITY_PERIOD) {
Log.w(TAG, "Scheduling delayed notification...");
executor.execute(new DelayedNotification(context, masterSecret, threadId));
executor.execute(new DelayedNotification(context, threadId));
} else {
updateNotification(context, masterSecret, threadId, true);
updateNotification(context, threadId, true);
}
}
public static void updateNotification(@NonNull Context context,
@Nullable MasterSecret masterSecret,
long threadId,
boolean signal)
{
@@ -229,12 +225,11 @@ public class MessageNotifier {
if (isVisible) {
sendInThreadNotification(context, threads.getRecipientForThreadId(threadId));
} else {
updateNotification(context, masterSecret, signal, 0);
updateNotification(context, signal, 0);
}
}
private static void updateNotification(@NonNull Context context,
@Nullable MasterSecret masterSecret,
private static void updateNotification(@NonNull Context context,
boolean signal,
int reminderCount)
{
@@ -254,7 +249,7 @@ public class MessageNotifier {
return;
}
NotificationState notificationState = constructNotificationState(context, masterSecret, telcoCursor);
NotificationState notificationState = constructNotificationState(context, telcoCursor);
if (signal && (System.currentTimeMillis() - lastAudibleNotification) < MIN_AUDIBLE_PERIOD_MILLIS) {
signal = false;
@@ -265,13 +260,13 @@ public class MessageNotifier {
if (notificationState.hasMultipleThreads()) {
if (Build.VERSION.SDK_INT >= 23) {
for (long threadId : notificationState.getThreads()) {
sendSingleThreadNotification(context, masterSecret, new NotificationState(notificationState.getNotificationsForThread(threadId)), false, true);
sendSingleThreadNotification(context, new NotificationState(notificationState.getNotificationsForThread(threadId)), false, true);
}
}
sendMultipleThreadNotification(context, notificationState, signal);
} else {
sendSingleThreadNotification(context, masterSecret, notificationState, signal, false);
sendSingleThreadNotification(context, notificationState, signal, false);
}
cancelOrphanedNotifications(context, notificationState);
@@ -287,7 +282,6 @@ public class MessageNotifier {
}
private static void sendSingleThreadNotification(@NonNull Context context,
@Nullable MasterSecret masterSecret,
@NonNull NotificationState notificationState,
boolean signal, boolean bundled)
{
@@ -296,7 +290,7 @@ public class MessageNotifier {
return;
}
SingleRecipientNotificationBuilder builder = new SingleRecipientNotificationBuilder(context, masterSecret, TextSecurePreferences.getNotificationPrivacy(context));
SingleRecipientNotificationBuilder builder = new SingleRecipientNotificationBuilder(context, TextSecurePreferences.getNotificationPrivacy(context));
List<NotificationItem> notifications = notificationState.getNotifications();
Recipient recipient = notifications.get(0).getRecipient();
int notificationId = (int) (SUMMARY_NOTIFICATION_ID + (bundled ? notifications.get(0).getThreadId() : 0));
@@ -313,8 +307,7 @@ public class MessageNotifier {
long timestamp = notifications.get(0).getTimestamp();
if (timestamp != 0) builder.setWhen(timestamp);
builder.addActions(masterSecret,
notificationState.getMarkAsReadIntent(context, notificationId),
builder.addActions(notificationState.getMarkAsReadIntent(context, notificationId),
notificationState.getQuickReplyIntent(context, notifications.get(0).getRecipient()),
notificationState.getRemoteReplyIntent(context, notifications.get(0).getRecipient()));
@@ -411,15 +404,12 @@ public class MessageNotifier {
}
private static NotificationState constructNotificationState(@NonNull Context context,
@Nullable MasterSecret masterSecret,
@NonNull Cursor cursor)
{
NotificationState notificationState = new NotificationState();
MessageRecord record;
MmsSmsDatabase.Reader reader;
NotificationState notificationState = new NotificationState();
MmsSmsDatabase.Reader reader = DatabaseFactory.getMmsSmsDatabase(context).readerFor(cursor);
if (masterSecret == null) reader = DatabaseFactory.getMmsSmsDatabase(context).readerFor(cursor);
else reader = DatabaseFactory.getMmsSmsDatabase(context).readerFor(cursor, masterSecret);
MessageRecord record;
while ((record = reader.getNext()) != null) {
long id = record.getId();
@@ -495,14 +485,14 @@ public class MessageNotifier {
public static final String REMINDER_ACTION = "org.thoughtcrime.securesms.MessageNotifier.REMINDER_ACTION";
@SuppressLint("StaticFieldLeak")
@Override
public void onReceive(final Context context, final Intent intent) {
new AsyncTask<Void, Void, Void>() {
@Override
protected Void doInBackground(Void... params) {
MasterSecret masterSecret = KeyCachingService.getMasterSecret(context);
int reminderCount = intent.getIntExtra("reminder_count", 0);
MessageNotifier.updateNotification(context, masterSecret, true, reminderCount + 1);
int reminderCount = intent.getIntExtra("reminder_count", 0);
MessageNotifier.updateNotification(context, true, reminderCount + 1);
return null;
}
@@ -516,22 +506,19 @@ public class MessageNotifier {
private final AtomicBoolean canceled = new AtomicBoolean(false);
private final Context context;
private final MasterSecret masterSecret;
private final Context context;
private final long threadId;
private final long delayUntil;
private final long threadId;
private final long delayUntil;
private DelayedNotification(Context context, MasterSecret masterSecret, long threadId) {
this.context = context;
this.masterSecret = masterSecret;
this.threadId = threadId;
this.delayUntil = System.currentTimeMillis() + DELAY;
private DelayedNotification(Context context, long threadId) {
this.context = context;
this.threadId = threadId;
this.delayUntil = System.currentTimeMillis() + DELAY;
}
@Override
public void run() {
MessageNotifier.updateNotification(context, masterSecret);
MessageNotifier.updateNotification(context);
long delayMillis = delayUntil - System.currentTimeMillis();
Log.w(TAG, "Waiting to notify: " + delayMillis);
@@ -542,7 +529,7 @@ public class MessageNotifier {
if (!canceled.get()) {
Log.w(TAG, "Not canceled, notifying...");
MessageNotifier.updateNotification(context, masterSecret, threadId, true);
MessageNotifier.updateNotification(context, threadId, true);
MessageNotifier.cancelDelayedNotifications();
} else {
Log.w(TAG, "Canceled, not notifying...");