12 Sicherheitsprinzipien auf einen Blick

Apps verarbeiten eine Menge sensibler Daten. Daher führt kein Weg an Mobile App Security vorbei. Vergangenes Jahres hatte ich das Glück tiefer in dieses Thema in einer internen Schulung der Süddeutschen Zeitung einzutauchen.

In einem Workshop lag der Fokus auf Mobile Security. Hierbei ging es darum, mögliche Sicherheitsrisiken in Apps zu identifizieren und diese Thematik auch in zukünftigen Konzeptionen mehr zu berücksichtigen. In diesem Blogeintrag möchte ich ein paar Eindrücke und Learnings daraus vorstellen:

Warum Mobile Security?

Prinzipiell können Apps auf zwei Arten angegriffen werden:

  • Auf dem mobilen Gerät (in der Regel zur Laufzeit)
  • aber auch offline, indem eure Binärdatei (also die APK oder IPA) auf Sicherheitslücken hin durchleuchtet wird.

Deswegen sollte man sich kontinuierlich darüber informieren, welche Sicherheitslücken eine App angreifbar machen können. Einen guten Anlaufpunkt dafür bietet die Seite der OWASP Foundation.

Hier werden in regelmäßigen Abständen die Top 10 Sicherheitslücken in der mobilen Entwicklung aufgeführt. Ein Blick lohnt sich also. Vielleicht erkennt ihr ja in der Liste einen Punkt, den ihr in eurer App mal genauer unter die Lupe nehmen solltet.

Sicherheitsprinzipien in der App Entwicklung

Als erstes haben wir uns einige Sicherheitsprinzipien angeschaut. Diese sind nicht nur auf die Appentwicklung beschränkt! Auch in anderen Bereichen finden diese ihre Anwendung und sind somit für alle Software Entwickler*in relevant.

1. Setze sichere Defaults

Entwickle deine Software so, dass die Standardeinstellungen absolut sicher sind. Erst eine bewusste Konfigurationsänderung sollte die Software potentiell unsicherer machen.

2. Trenne Verantwortlichkeiten (Separation of Duties)

Ein modulares System ist einfacher abzusichern. Wenn Funktionalitäten in separate Komponenten getrennt werden, kann ein*e Angreifer*in nur mit einem Teil der Funktionalität arbeiten. Auch die Einführung von Rollen/Rechten kann hier helfen.

3. Gib jedem nur die minimalen Rechte (Least Privilege)

Jede*r Benutzer*in und jedes System sollen zu jedem Zeitpunkt nur die Rechte haben, die absolut notwendig sind. Je länger ein*e Benutzer*in oder eine Komponente mit kritischen Rechten arbeitet, desto höher ist die Wahrscheinlichkeit, dass sie missbraucht werden.

4. Vermeide Security by Obscurity

Obfuskierung kann die Sicherheitsmaßnahmen zwar ergänzen, aber man sollte sich nicht allein darauf verlassen.

5. Erstelle mehrere Verteidigungslinien (Defense in Depth)

Nutze mehrere Verteidigungslinien hintereinander (z.B. VPN → HTTPS → zusätzliche Verschlüsselung). So steht der Angreifer nach einem erfolgreichen Durchbruch vor der nächsten Wand.

Damit steigt die Wahrscheinlichkeit, dass er aus Frustration aufgibt. Die angewendeten Methoden sollten jedoch verhältnismäßig sein, da sie die Komplexität des Systems steigern.

6. Vertraue nur dem Backend

Autorisierung und Authentifizierung, Eingabenvalidierung und andere Sicherheitsmechanismen sollten nur auf dem Backend ausgeführt werden. Dieses ist nicht so leicht anzugreifen und unter der Kontrolle der Entwickler*in steht.

7. Baue keine Hintertüren

Sicherheitskritische Feature-Flags oder Debug User mit speziellen Rechten sollten vermieden werden. Diese sind potentielle Sicherheitslücken im Produktivcode.

8. Sichere Fehlerbehandlung

Nach einem Fehler sollte das System in einen sicheren und definierten Zustand zurückfinden. Fehlermeldungen sollte keine sicherheitsrelevanten Informationen enthalten.

9. Minimiere die Angriffsfläche

Systemkomponenten, die nicht erreichbar sind oder gar nicht da sind, können nicht angegriffen werden. Es sollte deswegen überprüft werden, ob wirklich alle Komponenten benötigt werden. Falls doch, sollte die Sichtbarkeit der Komponente auf das Minimalste eingeschränkt werden.

10. Sei kritisch mit Fremdkomponenten

Komponenten, die man nicht selbst unter Kontrolle hat, bringen ein potentielles Sicherheitsrisiko mit sich. Sie sollten deswegen mit Vorsicht behandelt werden und speziell abgesichert werden.

11. Verwende etablierte Standards

Es sollten nur bewährte und verbreitete Bibliotheken mit den aktuellen Updates verwendet werden.

12. Validiere Eingaben

Eingaben von Nutzer*innen sollten immer validiert werden, um Fehler und die Ausführung von potentiell bösartigen Scripten zu vermeiden.

Mobile App Security

Netzwerksicherheit

Dieser Teil der Schulung befasst sich mit Netzwerksicherheit. Dabei haben wir zwei konkrete Maßnahmen besprochen, mit denen man sich gegen Man-In-The-Middle-Angriffe absichern kann:

Certificate Pinning und Certificate Transparency.

Bei Certificate Pinning wird der Hash des Public Keys des Zertifikats in der App gespeichert und bei der Kommunikation mit dem Original verglichen. So geht man sicher, dass dieses nicht ausgetauscht worden ist. In Android sieht der dafür nötige Code in OkHttp folgendermaßen aus:

val certificatePinner: CertificatePinner = CertificatePinner.Builder()
    .add("api.jambit.com", "sha256/<fingerprint-of-server-certificate>")
    .build()

val client: OkHttpClient = OkHttpClient.Builder()
    .certificatePinner(certificatePinner)
    .build()

Der Nachteil am Certificate Pinning ist u.a., dass ein App Release notwendig ist, falls eine Fälschung des Zertifikats festgestellt wird. Deswegen haben wir uns noch eine zweite Methode angeschaut, die dieses Problem umgeht.

Certificate Transpareny ist ein Prozess, der vorsieht, dass die Erstellung von Zertifikaten in einem offenen Log protokoliert wird. Eigentümer*innen können Zertifikats-Fälschungen über ein Monitoring feststellen. Clients können die Gültigkeit des Serverzertifikats über die Logserver sicherstellen.

Das Prinzip ist simpel: Wenn das Erstellen des Zertifikats transparent durchgeführt wird, dann ist es schwerer den Prozess zu manipulieren. Sollte doch eine Fälschung festgestellt werden, dann muss der Inhaber aktiv werden und es widerrufen. Eine Android Library, die bei der Implementierung unterstützt gibt es beispielsweise bei github.

Webviews

Webviews bringen besondere Sicherheitsrisiken mit sich bringen. Aus diesem Grund wurde auch auf deren Sicherheitsaspekte gesondert in der Schulung eingegangen. Webviews sind Systemkomponenten, die es erlauben, Webinhalte in einer App anzuzeigen. Sie sind angreifbar durch Sicherheitslücken in der App UND im Web.

Aber sie sind immerhin einigermaßen sicher vorkonfiguriert und durch das Betriebssystem geschützt.

In Android ist beispielsweise die Standardkonfiguration, dass Javascript deaktiviert ist, die Network Security Configuration erzwungen ist (ab Android 7), HTTPS erzwungen ist (ab Android 8) und der Dateizugriff deaktiviert ist (ab Android 11).

Außerdem läuft der Rendering Prozess in einer eigenen Sandbox ohne Internetzugriff und beschränkten Schreib- und Systemzugriffsrechten. Möchte man noch mehr Sicherheit, muss ein*e Entwickler*in selbst aktiv werden. Zusätzliche Absicherungen können sein:

  • Whitelisting: Man erlaubt nur vordefinierte URL-Schemes, nur HTTPS usw.
  • Lokale Daten und Cache der Webview löschen, wenn sie nicht mehr benötigt werden
  • Falls man ein JavascriptInterface verwendet: Auf HTML Message Channels portierten (Empfehlung von Google)
  • Javascript validieren und testen
  • Safe Browsing aktivieren
Mobile Security Datenspeicherung

Datenspeicherung

Folgende Beispiele gibt es für Daten, die gespeichert werden müssen:

  • Personenbezogene Daten (Kontaktdaten, Bankdaten etc.)
  • App States (z.B. SavedStateHandle in Android)
  • Logs/Metriken
  • Credentials
  • Nutzereinstellungen
  • Große Daten (z.B. Bilder)

Als Faustregel gilt bei der Datenspeicherung: Man sollte sicherheitskritische Daten nur wenn unbedingt notwendig in der App speichern. Mobile Geräte sind durch Revers-Engineering, Trojaner und/oder unvorsichtige Nutzer*innen gefährdet.

Daher ist das Backend ein besserer Ablageort für solche Daten. Falls es keine Alternative zum lokalen Speichern der Daten gibt, kann man in Android bspw. auf folgende Mechanismen zugreifen:

  • Passwörter können im Android KeyStore verschlüsselt abgelegt werden
  • Kleinere Daten (z.B. API Keys) können in den EncyrptedSharedPreferences abgelegt werden
  • Große Dateien können als EncryptedFile angepeichert werden

Hier ist ein Beispiel wie man Dateien in den EncyrptedSharedPreferences ablegen kann:

val masterKey: MasterKey = MasterKey.Builder(context)
    .setKeyScheme(MasterKey.KeyScheme.AES256_GCM)
    .build()

val sharedPreferences: SharedPreferences = EncryptedSharedPreferences.create(
    context,
    "secret_shared_prefs",
    masterKey,
    EncryptedSharedPreferences.PrefKeyEncryptionScheme.AES256_SIV,
    EncryptedSharedPreferences.PrefValueEncryptionScheme.AES256_GCM
)

sharedPreferences.edit().putString("myPassword", "secret123").apply()

Obfuskierung

Als Obfuskierung bezeichnet man verschiedene Techniken, um den Quellcode einer Software zu verschleiern und zu verändern, um es so anderen Programmierer*innen schwerer zu machen ihn zu verstehen.

Auf diese Weise können besonders wertvolle Algorithmen geschützt werden. So macht man es der Konkurrenz schwerer Code zu kopieren, um Kosten zu sparen. In Android gibt es verschiedene teils kostenpflichtige Tools, um Obfuskierung umzusetzen:

  • ProGuard
  • R8
  • DexGuard (kostenpflichtig)
  • DashoO (kostenpflichtig)

Die kostenpflichtigen Tools enthalten bessere Algorithmen und mehr Funktionen z.B. zur Verschlüsselung von Strings.

Da nativer Code wesentlich schwerer zu reengineeren ist, empfiehlt es sich besonders wertvollen Code in C/C++ auszulagern.

Obfuskierung ist eine sinnvolle Ergänzung, jedoch sollte man die Appsicherheit nicht von Obfuskierung abhängig machen. Besser ist es wertvolle Algorithmen im Backend zu implementieren.

Die kostenpflichtigen Tools bieten zwar mehr Sicherheit als die gratis Alternativen. Allerdings gibt es auch hier keine hundertprozentige Sicherheit. Es gibt beispielsweise Deobfuskatoren, die den Code wieder lesbar machen. Somit sollte Obfuskierung als zusätzliche Schutzwall gesehen werden, man sollte sich aber nicht allein darauf verlassen.

Mein persönliches Fazit

Für mich waren es ein spannende Schulung mit wichtigen Inhalten zu Security Aspekten einer App. Vielen Dank an den Veranstalter Maiborn Wolff! Einige der Themen hatte ich bereits gehört – es war aber auch einiges neues dabei. Ich hoffe, ihr konntet beim Lesen ein paar Themen mitnehmen, die ihr auch in eurer App nochmal genau unter die Lupe nehmen werdet.

SCHREIB UNS

* Pflichtfeld

SCHREIB UNS

* Pflichtfeld

Cookie-Einstellungen

Diese Website verwendet Cookies, um Inhalte und Anzeigen zu personalisieren, Funktionen für soziale Medien anbieten zu können und Zugriffe auf die Website zu analysieren. Zudem werden Informationen zu Ihrer Verwendung der Website an Partner für soziale Medien, Werbung und Analysen weitergegeben. Die Partner führen diese Informationen möglicherweise mit weiteren Daten zusammen, die Sie ihnen bereitgestellt haben oder die sie im Rahmen Ihrer Nutzung der Dienste gesammelt haben.

Weitere Informationen finden Sie in unserer Datenschutzerklärung. Dort können Sie nachträglich auch Ihre Cookie-Einstellungen ändern.

contact icon

Kontakt aufnehmen