Medienbildung und Informatik

Fol­gen­de Auf­ga­ben haben Pro­gram­mier­an­fän­ger von mir nach ca. vier Ein­hei­ten Python bekom­men. Das Bei­spiel zeigt — fin­de ich — ganz gut, dass Medi­en­kom­pe­tenz und Infor­ma­tik sich sehr gut ergän­zen kön­nen, teil­wei­se viel­leicht sogar ein­an­der bedin­gen. Das Pro­blem der Pass­wort­län­ge und dem Pass­wort­auf­bau wird hier bewusst nicht ange­spro­chen, weil das pro­gram­mier­tech­nisch etwas anspruchs­vol­ler ist. Das kommt dann in der Fol­ge­stun­de.
Wei­ter­hin ist natür­lich auch das sha-2-Ver­schlüs­se­lungs­ver­fah­ren moder­ne­ren Ent­wick­lun­gen wie z.B. pbkdf2 weit unter­le­gen, aber auch pro­gram­mier­tech­nisch wesent­lich beherrsch­ba­rer. sha512 ist schon ganz ok, auch wenn heu­ti­ge Gra­fik­kar­ten ca. 200 Mil­lio­nen Schlüs­sel pro Sekun­de berech­nen.

Kryptografie

Immer wie­der hörst du davon, dass bei gro­ßen Anbie­tern Daten­bank­in­hal­te gestoh­len wer­den. In dem Arti­kel steht aller­dings nichts davon, dass Pass­wör­ter gestoh­len wer­den, son­dern Hash­es. Heu­te wirst du ler­nen, dass du jetzt schon ganz ein­fach viel bes­ser sein kannst als Lin­kedIn und das mit nur ganz weni­gen Code­zei­len in Python.

Um alles mög­lichst gut zu ver­ste­hen, musst du auf jeden Fall die bei­den oben ver­link­ten Arti­kel lesen oder wenigs­tens über­flie­gen.

Aufgabe 1:

Nimm eines dei­ner Pass­wör­ter und las­se fol­gen­des Pro­gramm lau­fen (z.B. auf https://try.jupyter.org ).

1
2
3
4
5
6
7
# wir weisen Python an, Kryptografiefunktionen zu laden
import hashlib
# wir fragen nach einem Passwort
crypted_phrase = input()
# Und geben den Hash des Passworts als MD5-Hash aus
print("Hash is:")
print(hashlib.md5(crypted_phrase.encode('utf-8')).hexdigest())

Nimm jetzt den Hash und kopie­re ihn auf die­se Sei­te. Nach Ein­ga­be der Sicher­heits­ab­fra­ge (reCap­t­cha) kannst du schau­en, ob der Hash dei­nes Pass­worts bereits bekannt ist (Wenn du das Ver­fah­ren mit dem Pass­wort „12345678“ durch­führst, wirst du sehen, dass das „geknackt“ wird.

Wie­der­ho­le das Ver­fah­ren mit einem dei­ner Pass­wör­ter und fol­gen­dem Pro­gramm (mit „12345678“ klappt es! — auch mit dei­nem Pass­wort?):

1
2
3
4
5
6
7
# wir weisen Python an, Kryptografiefunktionen zu laden
import hashlib
# wir fragen nach einem Passwort
crypted_phrase = input()
# Und geben den Hash des Passworts als MD5-Hash aus
print("Hash is:")
print(hashlib.sha512(crypted_phrase.encode('utf-8')).hexdigest())

Wenn dein Pass­wort auch im zwei­ten Fall „geknackt“ wur­de, hast du ein Pro­blem, wenn du Opfer eines Daten­bank­dieb­stahls wirst. Auch dein Anbie­ter wird nur Hash­es in einer Daten­bank spei­chern.

Infor­mie­re dich jetzt über den Unter­schied zwi­schen dem md5- und dem sha512-Ver­schlüs­se­lungs­ver­fah­ren. Python kann fol­gen­de Ver­fah­ren „von Natur aus“: md5, sha1, sha224, sha256, sha384, sha512.

Aufgabe 2:

Das Pro­blem ist schon lan­ge gelöst — mit nur weni­gen Code­zei­len mehr. Infor­mie­re dich über den Begriff „Salt“ in Ver­bin­dung mit Hash­es.

1
2
3
4
5
6
import hashlib
# Statt "somestring" kannst bzw. solltest du möglichst wirres Zeug hier reinschreiben
salt = "somestring"
crypted_phrase = input()
salted_password = crypted_phrase + salt
print(hashlib.md5(salted_password.encode('utf-8')).hexdigest())

Wenn du jetzt ver­suchst, den Hash cra­cken zu las­sen, klappt das nicht mehr, weil ein soge­nann­test „salt“ (Salz) zum Pass­wort hin­zu­ge­fügt wird. Bei unse­rem Pro­gramm ver­wen­det jedes Pass­wort jedoch den glei­chen Salt.

Auch dafür gibt es eine Lösung:

1
2
3
4
5
6
import hashlib, uuid
# Python schreibt nun für dich wirres Zeug hier hinein
salt = uuid.uuid4().hex
crypted_phrase = input()
salted_password = crypted_phrase + salt
print(hashlib.md5(salted_password.encode('utf-8')).hexdigest())

Hät­ten Lin­kedIn und ande­re die Benut­zer­pass­wör­ter mit einem siche­ren Algo­rith­mus (z.B. sha512) gehasht und mit einem Salt ver­se­hen, wäre der Dieb­stahl der Daten­ban­ken nicht so ein gro­ßes Pro­blem, da es sehr lan­ge dau­ern wür­de, die Pass­wör­ter aus den Hash­es zu errech­nen.

In der Pra­xis spei­chert man die Salts im Klar­text zusam­men mit den Hash­es, meist durch ein Trenn­zei­chen abge­setzt. Du kannst ja ein­mal über­le­gen, war­um das kein Pro­blem dar­stellt.

Aufgabe 3:

Schrei­be fol­gen­de Pro­gram­me

  1. Es wird zwei­mal ein Pass­wort abge­fragt und dazu ein Hash berech­net. Stim­men bei­de Hash­es (und damit die Pass­wör­ter) über­ein, soll das Pro­gramm die Aus­ga­be „Access gran­ted!“ machen, ansons­ten „Access denied!“ aus­ge­ben.
  2. Ein Pro­gramm fragt nach einem „Mas­ter­pass­wort“ (pass­word) und einem Domain­na­men (salt). Es berech­net dar­aus einen Hash, den man als Pass­wort für die betref­fen­de Web­sei­te benut­zen kann — wenn man immer das rich­ti­ge Mas­ter­pass­wort und den glei­chen Domain­na­men ein­gibt — qua­si ein ganz ein­fa­cher Pass­wort­ma­na­ger!