Skip to content
Artwork for Schlüsseltechnologie

Schlüsseltechnologie

Xyrillian Noises

Die IT hat unser Leben in den letzten Jahrzehnten von Grund auf verändert. Aber wie funktioniert sie wirklich? Das möchte ttimeless mal erklärt bekommen. Zum Glück hat Xyrill Antworten.

Play
  • 20 episodes
  • monthly
  • Avg 1 hr 8 min
  • German
  • S1 · E94
    August 13 · 1 hr

    STP094: Vertrauenswürdiger Code

    Der Vertrauende macht Aspekte seines Wohlergehens und seiner Sicherheit vom Verhalten des Kooperationspartners abhängig, sagt die Wikipedia. Der vertrauen wir ja bekanntlich. Was könnte man aber tun, wenn der Kooperationspartner nicht menschlich und somit schwierig einzuschätzen ist? Ihr könnt jedenfalls sicher sein, dass auf diesem Kanal nur von uns notarisierte Inhalte verbreitet werden. Shownotes Prolog: in der IT-Sicherheit meist der Angreifer im Vorteil, weil vielfache Wiederholung bzw. Fächerung von Angriffen vergleichsweise einfach ist und am Ende nur einer durchkommen muss offensive Verteidigung ("Hackback") problematisch aufgrund schwieriger Attributierung (wenn der Angreifer keine offensichtlichen Fehler macht), also defensive Strategien notwendig bisher zur Angriffsseite: STP049 Schadcode, STP051 Ablauf eines IT-Angriffs bisher zur Verteidigungsseite: STP023 Virtualisierung (und darin Sandboxing), STP038 Software-Tests, STP078/080 Common Weakness Enumeration heute heben wir wieder den Schild anstelle des Schwertes Code Signing Idee: nur Code aus vertrauenswürdigen Quellen ausführen vgl. STP048: Vertrauen klassischerweise durch eine PKI nach X.509 (analog zu Transportverschlüsselung TLS bei Webseiten) als Wurzelzertifikatsautorität tritt der Plattformbetreiber auf, z.B. der App-Store-Betreiber oder bei Kerneltreibern der Betriebssystem-Hersteller Seitenleiste: die entsprechenden Signaturschlüssel sind sicherheitskritisch und werden heutzutage meist in HSM (Hardware-Sicherheitsmodulen) aufbewahrt Problem: Was bringt eine signierte Programmdatei, wenn die Ausführungsumgebung schon kompromittiert ist? Idee: Secure Boot und vergleichbare Technologien schon der Prozessor selber kann beim Start Code-Signaturen prüfen, ab dann Code Signing auf allen Ebenen über das Betriebssystem bis zum Anwendungsprogramm Vorteile von Code Signing und Secure Boot: verhindert bestimmte Einschlesungspfade für Malware (z.B. wenn man "libreoffice download" sucht und nicht die offizielle LibreOffice-Webseite findet, sondern eine legitim wirkende Virenschleuder) verhindert bestimmte Methoden für Lateral Movement und Persistierung (selbst wenn ein Prozess kompromittiert ist, kann er nicht zum Beispiel neue Programmdateien mit Malware auf die Platte schreiben und ausführen) Nachteile von Code Signing und Secure Boot: kein perfekter Schutz (aber was ist das schon) Ablauf des signierenden Zertifikats könnte ansonsten unveränderte Systeme funktionsunfähig machen -> deswegen bei Code Signing meist nur Prüfung auf "Signatur vor Ablauf", nicht auf "aktuelle Zeit vor Ablauf" erlaubt Willkür seitens der Geräte- bzw. Betriebssystemhersteller (siehe z.B. Entfernung von ICEBlock aus dem iOS-App-Store) zieht Eigentümerschaft am Gerät in Zweifel; vgl. Jay Freemans Diktum von "Felony Contempt of Business Model" ("verbrecherische Missachtung des Geschäftsmodells") zur Beschreibung des Effektes von DMCA Section 1201 und vergleichbaren Gesetzen (in Dtl. § 95a UrhG), welches die Umgehung von "wirksamen technischen Maßnahmen" zum Schutz von Urheberrechten kriminalisiert ganz anderer Ansatz: Reduktion der Trusted Computing Base (TCB) ("vertrauenswürdige Rechenbasis" bzw. eher "der man vertrauen muss") TCB: "die Gesamtmenge an Hardware und Software, die für den sicheren Betrieb eines Systems essentiell sind" nicht ganz dasselbe wie "weniger Programmcode = weniger Programmierfehler" z.B. bei Sandboxing ist nur die Sandbox selber Teil der PCB; Code innerhalb der Sandbox sollte dann (hoffentlich!) auch im Fehler- oder Infektionsfall keinen Schaden anrichten können praktisches Beispiel: in meinem LDAP-Server Portunus gibt es einen Teil, der mit Root-Rechten ausgeführt werden muss; dort habe ich mal reguläre Ausdrücke (vgl. STP021) durch explizite Parser ersetzt, weil das Entfernen der Regex-Bibliothek das Root-Binary um 10-15% verkleinert hat Randbemerkung: TCB-Reduktion ist auch, warum ich lieber 100 Zeilen Code selber schreibe, als eine Bibliothek zu importieren, die die eine Sache macht, die ich brauche... und dann noch zig andere Sachen mit unzähligen weiteren Abhängigkeiten (Symbolbild) Videoempfehlung für diese Art, über Software nachzudenken: Fefe über "Das Nützlich-Unbedenklich-Spektrum" in den Lektionen einiger Überlapp mit "Vom Mythos des Mann-Monats" (vgl. STP068/STP074/082) aber mit deprimierendem Einschlag: "Angenommen, jemand findet einen Weg, besser mit Komplexität umzugehen. Was passiert dann? Schreiben wir dann alle die alte Software neu, aber besser? Nein! Wir schreiben dann neue, noch größere Software. Wieder am Limit dessen, was mit den neuen Methoden machbar ist." (Der Talk ist von 2019. Jede Parallele zu Coding-Agenten ist rein zufällig.) Xyrills Favorit: die Wortprägung "Bugwelle" für die immer größer werdende Flut von Bugreports, die ein langlaufendes Softwareprojekt vor sich herschiebt

  • S1 · E93
    July 23 · 2 hr 8 min

    STP093: Historische Bindemittel

    Es wurde in der vorangegangenen Holzfolge angedroht und hier ist sie nun: die Folge über Leime. Allerdings natürlich nicht vollständig, sondern eher mit verstärkem Bezug zu vergangenen Techniken und Technologien. Wie passend, dass Ajuvo und Damals™ mit dabei ist. Shownotes Impressionen aus der Aufnahmesituation: Und nun die eigentlichen Shownotes: Trocknen vs. Härten Trocknung ist ein physikalischer Prozess, Verdunstung des Löse- oder Verdünnungsmittels, meist reversibel und zerstörungsfrei wieder lösbar Härten ist ein chemischer Prozess, Reaktion des Bindemittels mit Luft oder anderen eingesetzten Materialien, meist irreversibel, lösen der Verbindung ist mit Zerstörung des Materials verbunden Bindemittel allgemein: "Man kann mit allem malen, was pappt." – Bindemittel kann alles sein, dass sowohl inneren Zusammenhalt hat (Kohäsion) als auch an den verarbeiteten Materialien anhaftet (Adhäsion) und sich sinnvoll verarbeiten lässt. Mineralische Bindemittel Kalk (CaC0₃ → CaO→ Ca(OH)₂ → CaCO₃) Gips CaSO₄ Silikat (Wasserglas, Quarzsand mit Pottasche geschmolzen) Zement Öle (fette und ätherische) trocknende Öle Leinöl gewonnen aus den Samen der Leinpflanze seit langer Zeit als Oberflächenüberzug und für Farben gebräuchlich bildet einen hochelastischen und dauerhaften Polymerfilm auch für den Salat geeignet Tungöl, auch chinesisches Holzöl wiederstandsfähiger als Leinöl neigt aber als Malschicht etwas zur Versprödung in flüssiger Form giftig aber nach dem Trocknen unbedenklich Perillaöl ähnlich dem Leinöl aus den Samen asiatischen der asiatischen Perillapflanze halbtrocknende Öle Hanföl Mohnöl Sonnenblumenöl Walnussöl nichttrocknende Öle Olivenöl Rapsöl … Harze pflanzlich Bernstein, versteinerte Harze die älter als 1 Milion Jahre sind Kopal, Sammelbezeichnung für verfestigte Harze von Laub- und Nadelbäumen Dammar, rezentes Baumharz südostasischer Dipterocarpaceen Mastix, Sekret von Pistaziensträuchern Sandarak, Exkret nordafrikanischer Coniferen Kolophonium, Kristaliner Destilationsrückstand von Terpentinen (Ausscheidungen von Coniferen) Farbharze Drachenblut, Rezentes rotes Farbharzaus den Früchten asiatischer Palmen Gummigutt, gelbes Farbharz aus dem Milchsaft der Garnicia Morella (Ostasien, Ceylon, Thailand) tierisch Schellack, Tierisches Exkret der ostasischen Stockläuse(Lackschildlaus) Wachse Bienenwachs Carnaubawachs Montanwachs … Seifen, basische Salze von Fettsäuren Öl wird durch Zugabe von Alkalien in Fettsäure und Glyzerin gespalten und wasserlöslich z.B. Marseiller Seife mit einem bestimmten Anteil Fettsäuren Da chemisch ähnlich lassen sich auch Wachse, Harze und Fette zumindest anverseifen, der Rest wird emulgiert (Punisches Wachs) Pflanzliche Leime (Kohlenhydrate) Stärken aus stärtkehaltigen Pflanzenteilen durch mahlen und waschen gewonnen können nach dem Einrühren in kaltes Wasser mit heißem Wasser verkleistert werden Weizen- Kartoffel- Mais- Reis- … Dextrine Abbauprodukte von Stärken seit 1850 als Malerleim in Aquarellfarben durch erwärmen auf 160-200°C: Röstdextine durch Aufschluss mit Säuren: Säuredextrine durch Abbau mit Diastase: Enzymdextrine Gummen, wasserlösliche Baumharze Gummiarabicum, Sekret von Akaziengewächsen aus Afrika oder Asien Kirschgummi, Exkret erkrankter Steinostbäume hauptsächich der Gattung Prunus Tierische Leime (Proteine) Eiweiß: Das Hühnereiweis selbst als Bindemittel verwendet, trocknet wasserunlöslich auf das Eigelb kann duch seinen hohen Lecitingahalt als Emulgator für Temperafarben genutzt werden Casein: Ein Bestandteil der Kuhmilch, wird durch chemische Fällung mit Lab, mineralischen Säuren oder natürliche Säuerung der Milch zu Quark oder als Pulverkasein gewonnen erhält seine Klebkraft durch alkalischen Aufschluss z.B. mit Hirschhornsalz(Amoniumcarbonat), Borax oder Kalk Glutinleime Das in "tierischen Rohstoffen" enthaltene Kollagen wird durch Kochen in wasserquellbares Glutin überführt Glutinleim ist löslich durch erwärmen der klassische Tischlerleim bereits im alten Ägypten in Verwendung Benennung meist nach eingesetztem Rohstoff Knochenleim Hautleim Lederleim Gelatine Fischleim

  • S1 · E92
    July 2 · 51 min

    STP092: Der Siegeszug der KI-Konnektionisten (Teil 2)

    Letzte Folge der Reihe. Heute mit Bilderzeugungsmodellen und der Erklärung, warum die später drankommen, obwohl sie eher da waren (zumindest in der breiten Nutzung). Außerdem noch mit ein paar abschleßenden Gedanken am Ende dieser Serie. Shownotes Nochmal zurück zum ersten KI-Winter (siehe STP091): Warum skalieren reine Perzeptrone schlecht? Bsp. Bildererkennung Bild in Thumbnail-Größe (z.B. 256 Pixel im Quadrat, 3 Farbkanäle) besteht aus 256 * 256 * 3 = 196608 Einzelwerten Abbildung im ersten Layer des Perzeptrons auf z.B. 1000 Neuronen würde das Training von 196 Millionen Gewichten erfordern, und das ist nur der erste Layer! so viele Gewichte können nur mit sehr vielen Eingabedaten sinnvoll trainiert werden -> enormer Rechenaufwand für Training und Inferenz Faltende neurale Netzwerke (Convolutional Neural Network, CNN, ConvNet) Idee 1: pro Layer nicht einfach alle Eingabewerte mit allen Ausgabeneuronen verknüpfen, sondern eine bestimmte Struktur vorgeben (und alle nicht dazu passenden Verbindungen verbieten), um die Menge von Gewichten zu reduzieren Idee 2: Mustererkennung basiert auf Merkmalen (Features), die unabhängig von ihrer genauen Position im Bild immer gleich erkannt werden sollen Faltungslayer (Convolution Layer): aus einer Eingabe mit N * N Werten fasst jedes Feature-Neuron eine Teilregion der Größe K * K zusammen (z.B. K = 11: 121 Gewichte pro Neuron); Anzahl von Ausgabeneuronen basierend auf der gewünschten Anzahl F unterschiedlicher Features entweder N * N * F (bei Abtastrate 1) oder geringer (bei weniger dichter Abtastung) alle Neuronen desselben Features verwenden dieselben Gewichte -> enorme Reduktion des Trainings- und Inferenzaufwands Zusammenfassungslayer (Pooling Layer): Reduktion einer Eingabe mit N * N * F Werten in z.B. N/2 * N/2 * F Werte durch Zusammenfassen von nichtüberlappenden Regionen (z.B. 2x2) hier keine trainierbaren Gewichte, sondern Vorauswahl einer Zusammenfassungsfunktion wie max oder avg am Ende meist einige Ebenen klassische Perzeptron-Layer mit voll trainierbaren Gewichten zwischen allen Neuronen Beispiel: Architekturen früher Bilderkennungssysteme Tuning-Entscheidungen: Anordnung der Layer, Anzahl der Features, Faltungsgrößen, Abtastraten, Aktivierungsfunktion (heute meist ReLU) ab 2015: Diffusionsmodelle grundsätzlicher Ansatz: durch den Datenraum gerichtete Diffusion von Daten von einem Startpunkt zu einem höherwertigen Endpunkt während des Trainings fängt man mit hochwertigen Daten an und fügt immer mehr Rauschen hinzu, wodurch die Daten von ihrem Ausgangszustand "wegdiffundieren" Modell wird darin trainiert, diesen Diffusionsprozess umzukehren im Bereich der Bildverarbeitung z.B. Super-resolution imaging (mit einem niedrig aufgelösten Bild als Startpunkt) oder Bilderzeugung (mit reinem Rauschen als Startpunkt) Problem: Wenn man mit nur Rauschen anfängt, wie entscheidet man, wo man hin will? 2021: CLIP (Contrastive Language-Image Pre-Training) Trainingsdatensatz: Bilder mit möglichst akkuraten Textbeschreibungen ihrer Inhalte gleichzeitiges Training von zwei Encoder-Transformern, die einmal Bilder und einmal Textbeschreibungen in Embeddings übersetzen Training der Encoder versucht, die Ähnlichkeit der Embeddings zwischen passenden Bildern und Textbeschreibungen zu maximieren und zwischen unpassenden Paaren zu minimieren Bilderzeugung aus Diffusion: Text-Encoder übersetzt den Prompt in ein Embedding, Diffusionsmodell denoised damit ein initial komplett verrauschtes Bild in das Ausgabebild beim Training des Diffusionsmodells muss zu den Trainingsbildern das Embedding der entsprechenden Beschreibung präsentiert werden mögliche Realisierung: Diffusionsmodell als Transformer mit Self-Attention innerhalb des Bildes und Cross-Attention zum Embedding der Textbeschreibung Videotipp: 3Blue1Brown zu Diffusionsmodellen; dort zum Beispiel zur Kodierung von "Negative Prompts" (z.B. "no extra fingers", "no JPEG compression residue") Der gespielte O-Ton ist aus Deutschlandfunk Hintergrund: "10 Jahre OpenAI: Wie ChatGPT mit KI die Welt verändert". Xyrills Abendgedanken: Nach dieser Ausarbeitung verstehe ich jetzt, warum die Konnektionisten Transformer als den Durchbruch schlechthin und als Allheilmittel einsetzen. Aber, nochmal aus Gary Marcus's Blogartikel, der in STP089 referenziert war: Für immer gefangen im Land der Korrelationen, können neurale Netzwerke niemals (egal, wie viel Daten oder Rechenleistung ihnen zur Verfügung stehen) in der Lage sein, kausale Beziehungen zu verstehen -- warum Dinge so sind, wie sie sind -- und daraus folgend kausale Schlussfolgerungen zu ziehen. Dieser kritische Teil der menschlichen Kognition ist, warum Menschen nur einmal die Straßenverkehrsregeln in einer Stadt lernen müssen, um dann in vielen anderen Städten sicher fahren zu können, argumentiert Marcus. Teslas Autopilot hingegen kann Milliarden von Kilometern an Fahrten aufzeichnen und trotzdem crashen, wenn er in ein unbekanntes Szenario gerät oder mit ein paar strategisch plazierten Aufklebern überlistet wird. Marcus plädiert dafür, stattdessen Konnektionismus und Symbolismus miteinander zu verbinden. Und weiter: Viele der Fortschritte heutiger KI-Modelle resultieren wahrscheinlich aus der Ausweitung des Einsatzes symbolischer Werkzeuge, und nicht aus mehr Skalierung. Riesige Infrastruktur-Investitionen wie Stargate basieren wahrscheinlich auf falschen Annahmen darüber, was tatsächlich den Fortschritt vorantreibt. Als Schlusswort dieselbe Kritik an der Skalierungshypothese, aber weniger technisch ausgedrückt, von Quinn Norton in "What we talk about when we talk about AI": Menschen sind anders. Trotz der Entlehnung von Nomenklatur aus der Biologie haben die neuralen Netzwerke, die im Training von KI verwendet werden, keine Neuronen der menschlichen Art. Der Unterschied ist erkennbar. Wir lernen Sprache, Lesen und Schreiben anhand eines winzigen Datensatzes, und dieser Prozess umfasst Mimikry, Gefühle, Kognition und Liebe. Da mag auch statistische Gewichtung vorkommen, aber wenn dem so ist, dann haben wir den entsprechenden Mechanismus noch nicht in unserem Verstand und unseren Gehirnen gefunden. Es erscheint unwahrscheinlich, dass es dort in einer ähnlichen Form existieren würde, da diese KI-Systeme so viel mehr Informationen und Rechenleistung aufwenden müssen, um zu tun, was ein Erstsemesterstudent mit ein bisschen Motivation hinbekommt. Motivation ist unser Problem, aber es ist niemals ein Problem für KI-Systeme. Sie machen immer weiter, bis ihre Befehle einen Endpunkt erreichen, und dann erstarren sie. KI-Systeme sind leblos zu Beginn, leblos währenddessen, und leblos am Ende.

  • S1 · E91
    June 11 · 1 hr 13 min

    STP091: Der Siegeszug der KI-Konnektionisten (Teil 1)

    Einige haben sich schon gefragt, wann denn nun die KI-Serie anfängt. Nun ja. Nachdem wir die letzten Male die Grundlagen besprochen haben, geht es nun im Sinne des aktuellen Zeitgeistes wirklich um KI. Zuerst im Bezug auf Text. Shownotes Damit wir uns nicht komplett verzetteln, beschränken wir uns in diesem Zweiteiler auf alle Entwicklungen, die zu den aktuellen Buzzword-Technologien geführt haben: Transformer und Diffusionsmodelle. KI-Winter: Flaute in der KI-Forschung nach dem Scheitern eines bestimmten Ansatzes frühe 1970er: erster KI-Winter nach Problemen mit dem Skalieren von Perzeptronen (Scheitern konnektionistischer Ansätze) späte 1980er: zweiter KI-Winter nach allgemeiner Ernüchterung über Expertensysteme (Scheitern symbolischer Ansätze) danach neuer Aufwind für konnektionistische Ansätze durch neue Optimierungen und Moore's Law (Skalierungshypothese) Rekurrente neurale Netzwerke (Recurrent Neural Network, RNN) Grundproblem: Wie geht man mit zeitlich geordneten Daten um, die sich entlang des Zeitstrahls kausal beeinflussen (z.B. Sprache, Aktienkurse)? Idee: neurales Netzwerk verarbeitet immer die Eingaben aus einem Zeitschritt und gibt zusätzlich zur Ausgabe einen internen Zustand aus, der beim nächsten Zeitschritt zur Eingabe wird Problem: Wie trainiert man das? Backpropagation funktioniert nicht, wenn Signale zu früheren Layern rückwärts geschickt werden frühe Ansätze hatten Probleme mit hohem Trainingsaufwand, weil Backpropagation in Schleifen laufen muss hier aus Zeitgründen nur der Ansatz, der heutzutage die größte Bedeutung hat 2014: seq2seq zum Übersetzen natürlicher Sprache zwei separate aufeinanderfolgende Schritte Encoder: Lesen jeweils eines Eingabesymbols (Token); hierbei keine Ausgabe, sondern nur Aktualisierung eines internen Zustands Decoder: Extraktion eines Ausgabetokens aus dem internen Zustand unter Präsentation des zuletzt generierten Tokens, dabei ebenfalls Aktualisierung des internen Zustandes Abwägung Vorteil: damit keine Probleme mit rückwärts laufenden Signalen, Training mit Backpropagation möglich Nachteil: interner Zustand muss die gesamte Eingabe darstellen können, bei langen Eingabesequenzen "vergisst" der interne Zustand Teile der Eingabe im Gespräch erwähnt: Hutter Prize Lösung: Attention; im Falle von seq2seq: interner Zustand nach jedem Encoding wird gemerkt Decoding aus dem aktuellsten internen Zustand (wie zuvor) ergibt ein vorläufiges Ergebnis, das mit einem Satz trainierbarer Gewichte in eine Query (Abfrage) überführt wird (anschauliche Interpretation z.B. "Wir generieren jetzt das Adjektiv, das vor 'Garten' steht. Wer weiß was?") analog dazu werden die gemerkten internen Zustände des Encodings mit einem anderen Satz trainierbarer Gewichte in einen Key (Schlüssel) überführt (anschauliche Interpretation z.B. "Ich bin ein Adjektiv.") ...und außerdem mit einem dritten Satz trainierbarer Gewichte in einen Value (Wert) (anschauliche Interpretation z.B. "Das zuletzt gesehene Adjektiv ist 'groß'.") Values, bei denen Query und Key gut aufeinanderpassen, werden mit Gewichtung aufaddiert zu einem Kontext: C = softmax(Q * K^T) * V mit Softmax-Funktion tatsächliches Ausgabezeichen aus Kombination des Kontext mit dem ursprünglichen Ergebnis des Decoding 2017: Transformer verwerfen die rekurrente Struktur und arbeiten nur mit Attention, um die Parallelisierbarkeit zu verbessern (daher der berühmte Paper-Name "Attention is all you need") jedes Eingabesymbol (Token) wird in ein Embedding überführt, einen hochdimensionalen Vektor (z.B. GPT-3: je nach Modellvariante zwischen 768 und 12288 Dimensionen) Ziel des Embedding: Darstellung von Konzepten in einem Vektorraum (Beispiel) bei autoregressiver Texterzeugung (autoregressiv = "aus sich selbst heraus"): Self-Attention auf den Embeddings der bis jetzt vorliegenden Tokenfolge (eventuell begrenzt durch das Context Window), Resultat ist ein aktualisierter Embedding-Vektor aber: Attention ist eine lineare Funktion und kann nicht als universeller Funktionsapproximator fungieren deswegen dahinter ein klassisches dicht verschaltetes Feed-Forward-Netzwerk, in dem die überwältigende Masse der trainierbaren Gewichte sitzt Ergebnis: der finale Embedding-Vektor, der in ein Token zurückübersetzt wird bei Texterzeugung anhand einer separaten Eingabesequenz (z.B. maschinelle Übersetzung, Spracherkennung, RAG) außerdem Cross-Attention zum Transfer von Informationen aus der Eingabesequenz in den Dekoder Abendgedanken aus "Large Language Models, Model Collapse and the Conservation of Information": Es ist überraschend, wieviele Probleme sich auf "das nächste Wort vorhersagen" reduzieren lassen (vgl. Meldungen der Form "Goldmedaille in der Matheolympiade"). Aber: LLMs wägen nicht ab, sie verarbeiten. statistische Aussagen auf Basis von Embeddings, nicht mehr und nicht weniger ungeeignet für symbolische Aufgaben wie Arithmetik LLMs überlegen nicht, sie rationalisieren. die statistische Natur der Sache ist gut für Induktion, aber schlecht für Deduktion LLMs können nicht endlose Informationen erzeugen.

  • S1 · E90
    May 21 · 1 hr 36 min

    STP090: Maschinelles Lernen vor der Jahrtausendwende

    Bevor wir dann wirklich zu dem kommen, was wir heute unter KI verstehen, geht es heut noch mal um die nun nicht mehr ganz so graue Vorzeit. Immerhin beginnen wir jetzt damit, Neuronen zu kitzeln und Liegestütze machen zu lassen. Nebenbei steuert Xyrill noch wertvolle Erziehungstipps bei. Shownotes 1943: mathematische Modellierung von Neuronen durch den Neurophysiologen Warren McCulloch und den Logiker Walter Pitts Bestandteile: mehrere Eingänge x_1 bis x_n und ein Ausgang y mit Logiksignalen (entweder 0 oder 1) Inferenz-Funktion: y = (∑_i w_i * x_i + b) > 0 mit Gewichten w_i und Bias b damit Teilung des Raumes der Eingabewerte in zwei Hälften entlang einer Gerade bzw. Hyperebene (Beispiel) Berechnung der Gewichte: Präsentation von Eingabewerten mit bekannten erwarteten Ausgabewerten (Supervised Learning, überwachtes Lernen) bei jeder falschen Inferenz (y erwartet, aber y' erhalten) Update der Gewichte gemäß w_i -> w_i + r * (y - y') * x_i mit Lernrate r Lernen des Bias wie ein Gewicht w_0 mit x_0 = 1 für alle Trainingsdatensätze Praxisbeispiel damit jede binäre Unterscheidung lernbar, die durch eine lineare Schwelle ausgedrückt werden kann Problem: verrauschte Daten -> nichtbinäre Ausgaben notwendig Problem: andere Arten binärer Funktionen, z.B. y = x_1 XOR x_2 -> Verkettung mehrerer Neuronen notwendig 1957: Verschaltung mehrerer "Neuronen" zu einem Perzeptron mehrstufige Verkettung von Neuronen erlaubt Lernen komplexerer Funktionen, z.B. erst Erkennung spezifischer Teile und dann in Folgeschritten Zusammensetzung zu einem großen Ganzen Problem: Wenn während des Trainings fehlerhafte Ausgaben produziert werden, wo muss man dann Gewichte anpassen? Idee: Fehlerrückführung (Backpropagation); wenn am Ende ein Fehler rauskommt, muss dieser anteilig auf frühere Neuronen zurückattributiert und dort zum Training genutzt werden hierfür Anwendung der Kettenregel (siehe STP089), z.B. in einem 2-Layer-Perzeptron Kettenregel geht nur auf ableitbaren Funktionen, deswegen nicht mehr binäres Ausgabesignal, sondern eine geglättete Stufenfunktion wie die Sigmoidfunktion z.B. Signale y3 der dritten Ebene sind eine Funktion der Signale y2 der zweiten Ebene, und so weiter Ableitung z.B. von y3(y2(y1(x))) ist dy3/dx = dy3/dy2 * dy2/dx; ausgehend vom Fehler Δy3 des Ergebnisses Training der Gewichte w3 und Ermittlung eines Fehlers Δy2 für die nächste Ebene Achtung: das ist eine extreme Verkürzung aus didaktischen Gründen; tatsächlich wird nicht dividiert, sondern das Anwenden des Gradient-Operators auf die Loss-Funktion führt zu einer Vertauschung der Multiplikationsreihenfolge, was partielle Rückwärtsevaluierung ermöglicht Randbemerkung 1: hier beginnt das Meme, dass maschinelles Lernen nur ein Haufen Matrixmultiplikationen ist (vgl. XKCD 1838) Randbemerkung 2: geglättete Stufenfunktionen erlauben eine Variation in der Stärke bzw. Breite der Glättung (Temperatur) 1990er-2010er: maschinelle Übersetzung natürlicher Sprache mit statistischen Modellen, die keine neuralen Netzwerke sind (Quelle: Xyrills Vorlesungsnotizen von 2016; passenderweise dasselbe Jahr, indem Google Translate auf neurale Netzwerke umstieg) diverse miteinander kombinierbare Modelle zur Beurteilung der Wahrscheinlichkeit gegebener Sätze in einer einzelnen Sprache (Sprachmodell) bzw. der Wahrscheinlichkeit, dass zwei Sätze in verschiedenen Sprachen Übersetzungen voneinander sind (Übersetzungsmodell) Kombination von Sprachmodell und Übersetzungsmodell gemäß des Noisy-Channel-Modell: z.B. gegeben einem deutschen Satz D Suche nach dem wahrscheinlichsten englischen Satz E: P(E|D) = P(E) * P(D|E) / P(D) (Satz von Bayes), P(E) gemäß Sprachmodell und P(E|D) gemäß Übersetzungsmodell und P(D) irrelevanter konstanter Faktor stochastische Suche nach E: z.B. Start mit leerem Satz, schrittweise Erweiterung um je ein Wort aus allen möglichen englischen Wörtern, Verwerfen der schlechtestbewerteten Optionen Bsp. eines Sprachmodells: Markow-Kette sukzessiver Aufbau eines Satzes durch Raten des nächsten Wortes (vgl. Autocomplete) Training bestimmt aus einem gegebenen Textkorpus die Wahrscheinlichkeiten von bestimmten Wortsequenzen einfachster Fall: Bigramm-Modell, z.B. P(Ich bin groß) = P(ɛ, Ich) * P(Ich, bin) * P(bin, groß) * P(groß, ɛ) Erweiterung: Hidden Markov Model mit einer versteckten Zustandsmaschine, die Wortarten versteht; z.B. P(Ich bin groß) = P(ɛ, Pronomen) * P(Pronomen, Ich) * P(Pronomen, Verb) * P(Verb, bin) * P(Verb, Adjektiv) * P(Adjektiv, groß) * P(Adjektiv, ɛ) Abwägung: größerer Lookback erhöht die Kohärenz, führt aber schnell zu Overfitting Fun Fact: dazu hat Xyrill eine Abschlussarbeit geschrieben Bsp. eines Übersetzungsmodells: IBM alignment models, hier der Einfachheit halber nur Modell 1 Training resultiert hauptsächlich in einer Wahrscheinlichkeitstabelle von Wortkorrespondenzpaaren z.B. P(Ich bin groß, I am big) = P(Ich, I) * P(bin, am) * P(groß, big) + (andere verschwindende Beiträge) Problem: versteht nicht grammatikalisch korrekte Wortreihenfolge, z.B. P(Ich bin groß, I am big) = P(Ich bin groß, I big am) Problem: versteht nicht Hilfswörter, die in der anderen Sprache keine Entsprechung haben Probleme mitigierbar durch Kombination mit Sprachmodell wie oben beschrieben Erweiterung durch Modell 2 bis 6 1980er: Expertensysteme, beispielhaft an der Programmiersprache Prolog Expertensystem: "ein Programm, das Menschen bei der Lösung komplexer Probleme wie ein Experte unterstützen kann, indem es Handlungsempfehlungen aus einer Wissensbasis ableitet", bzw. kürzer "eine logische Entscheidungsmaschine" Prolog: Programmiersprache, die nicht primär auf Zahlen oder Speicherbereichen arbeitet, sondern auf Fakten und Ableitungsregeln (siehe Beispiele im verlinkten Artikel) Einschätzung: Prolog-artige Sprachen sind ein nützliches Paradigma für sehr spezifische Anwendungsfälle, aber die explizite Kodierung von Wissen läuft erfahrungsgemäß schnell in ontologische Probleme

  • S1 · E89
    April 30 · 56 min

    STP089: Frühgeschichte der künstlichen Intelligenz

    Scheinbar ist die sogenannte KI etwas, was nicht ganz so schnell wieder weg geht. Daher fangen wir in dieser Episode damit an, etwas genauer zu erklähren, was es damit auf sich hat. Im ersten Teil dieser Reihe geht es um die entferntere Geschichte, die zu dem geführt hat, was wir heute sehen. Shownotes Der Einfachheit halber wird im gesamten Text "künstliche Intelligenz" als KI und "maschinelles Lernen" als ML abgekürzt. KI kann vieles heißen, siehe die Breite von Meilensteinen in Wikipedias Timeline of AI; ein paar Picks als initiale Motivation Jhd. v. Chr.: Aristoteles beschreibt den Syllogismus als Methode formalen, mechanistischen Denkens heutzutage Teil der Aussagenlogik 12./13. Jhd: Ramon Llull legt sein Hauptwerk Ars generalis ultima vor, das erläutert, wie man durch mechanisches Kombinieren von Begriffen mittels einer von ihm erdachten "logischen Maschine" zu Erkenntnissen gelangt Llull war sowohl Logiker als auch Theologe: "Die Große Kunst war Llull seinen Memoiren zufolge [...] 'von Gott offenbart' worden. Er wurde von da an auch Doctor illuminatus genannt." 1679: Leibniz stützt sich auf Llulls Arbeit und entwickelt ein "Alphabet der menschlichen Kognition", mit dem Argumente nach festen Regeln mechanistisch ableitbar sein sollen aber auch 1676: Leibniz leitet als Teil seiner Grundlagenforschung der Analysis die Kettenregel her theoretische Grundlage für das Training mehrschichtiger ML-Systeme damit durch Leibniz wichtige Vorarbeit für beide wesentlichen Lager der KI-Forschung, gemäß Einteilung von KI-Forscher Gary Marcus symbolische Tradition (seit dem Mittelalter, s.o.): "In diesem Ansatz stehen Symbole und Variablen für Abstraktionen; mathematische und logische Funktionen machen den Kern aus. [Symbolische] Systeme repräsentieren Wissen im Allgemeinen explizit, oft in Datenbanken, und verwenden klassische Programmiersprachen (oder sind komplett in diesen verfasst)." konnektionistische Tradition (seit 1940/1950): "[Konnektivistische] Systeme sind statistisch, sehr lose von bestimmten Aspekten des Gehirns inspiriert (z.B. sind 'Knoten' in neuralen Netzwerken als Abstraktion von Neuronen gedacht), und für gewöhnlich auf großen Datensätzen trainiert. Große Sprachmodelle (LLM) entwuchsen dieser Tradition." Marcus skizziert die Geschichte der KI-Forschung als eine Geschichte der Spannung zwischen diesen Denkschulen Xyrill beobachtet, dass dieser Dualismus zu seinen Beobachtungen über den Dualismus der menschlichen Intelligenz kongruent ist (vgl. System 1/2 in Daniel Kahnemans "Schnelles Denken, langsames Denken"; aber Vorsicht bzgl. Replizierbarkeit) 1956: Dartmouth Conference, ein zweimonatiges Sommerseminar zu KI nicht die erste wissenschaftliche Aktivität zu KI mit Computern, aber historischer Einfluss durch die hohe Konzentration wichtiger Vertreter des Feldes (analog zu den Solvay-Konferenzen in der Physik) allein der erste Absatz des Förderantrags umreißt auch aus heutiger Sicht akkurat das ganze Feld (siehe Link unter "Durchführung") Personen auf der Konferenz (Auswahl) John McCarthy: Erfinder der Programmiersprache LISP Marvin Minsky: Vordenker der Robotik, Miterfinder der Programmiersprache Logo (Caveat: Verbindung zu Epstein) Nathaniel Rochester: 1955 bei IBM Experimente mit Neuronalen Netzwerken, Mustererkennung, Spielprogrammen, etc. Claude Shannon: Begründer der Informationstheorie; 1950 Konstruktion einer Robotermaus, die ein Labyrinth durchschreiten konnte Ray Solomonoff: präsentierte auf der Konferenz ein Programm, dass "arithmetische Formeln durch Beispiele ohne eingreifende Aufsicht" lernen konnte Oliver Selfridge: schlug 1958 eine Struktur für KI-Systeme als Netzwerk von Agenten ("Dämonen") vor, mit unterschiedlichen Arten von Agenten ("Feature Demons" für Mustererkennung, "Cognitive Demons" für Informationszusammenführung, "Decision Demons" für Entscheidungen) Allen Newell und Herbert A. Simon: 1956 Entwicklung eines Logiksystems, das im Stande war, die 38 Theoreme aus Bertrand Russells Principia Mathematica zu beweisen (vgl. moderne Theorem-Löser wie Rocq)

  • S1 · E88
    April 9 · 39 min

    STP088: Die Schlüsseltechnologie-Kochshow

    Heute mal eine eher kurze Folge. Darin geht es ums Kochen und ähnliche Dinge und wie man sie verbinden könnte (oder auch nicht). Shownotes ttimeless kocht eines seiner geTeXten Rezepte: Präambel in einer Masterdatei Rezepte in einzelnen Dateien Hier das Hummusrezept wie von Andong auf seinem Youtube-Kanal vorgestellt: Can I Recreate the World's Smoothest Hummus?, dazu gibt es das passende Pita. Gesamtergebnis als PDF Xyrill kocht ein C++-Programm mit make(1): Grundproblem: im Kompilierungsmodell von C/C++ entsteht ein Programm in mehreren Schritten jede einzelne Quellcode-Datei wird einzeln vom Compiler in eine Objektdatei übersetzt am Ende werden alle Objektdateien vom Linker zu einer ausführbaren Programmdatei verknüpft als Beispiel ein kleines, vollständiges C-Programm Vorteile von Makefiles Universalsprache zum Dokumentieren von Prozessen Nachteile/Beschränkungen tw. arkane Syntax (fast?) turingvollständig, vgl. Ninja (unter anderem dadurch) vergleichsweise ineffizient, vgl. Tup moderne Programmiersprachen verwenden andere Kompilierkonzepte, meist fokussiert um Module aus mehreren Quelldateien

  • S1 · E87
    March 19 · 1 hr 15 min

    STP087: Graphen von Null bis Dijkstra

    Nachdem wir den Begriff schon ein paar Male gestreift haben, heute ein genauerer Blick auf Graphen. Darin: informierte und uninformierte Suche sowie eine Erkundung der Dresdner Umgebung. Shownotes oft erwähnt, aber nie systematisch eingeführt: der Begriff Graph Graph: eine Menge von Knoten mit Kanten dazwischen z.B. Nahverkehrsnetz: Knoten = Haltestellen, Kanten = Direktverbindung zwischen zwei Haltestellen z.B. soziale Medien: Knoten = Personen, Kanten = "ist befreundet/folgt" anders als bei Listen (STP077) oder Maps (STP079) große Variabilität darin, was ein Graph fundamental ist z.B. gerichtete vs. ungerichtete Graphen: Haben die Kanten eine Richtung oder nicht? (siehe Beispiele oben) häufig verwendete Unterarten von Graphen: Baum: ayzklischer ungerichteter zusammenhängender Graph (z.B. siehe STP077/STP079: zum effizienten Abspeichern von sortierten Listen bzw. Maps) azyklischer gerichteter Graph (z.B. Versionsverwaltung, Familienstammbaum, Firmen-Organigramm) planarer Graph: siehe "Untangle" Wie durchschreitet man einen Graphen? -> Suchalgorithmen, im allgemeinsten Fall die zwei wichtigsten "uninformierten" Suchalgorithmen Breitensuche: von einem Startpunkt pro Runde alle Nachbarn von bereits besuchten Knoten besuchen Tiefensuche: vom Startpunkt aus immer erst einen Nachbarn besuchen und dann dort wieder einen Nachbarn; sobald keine weiteren unbesuchten Nachbarn möglich sind, Backtracking zum vorherigen Knoten, bis ein neuer unbesuchter Nachbar gefunden wird sowohl Breiten- als auch Tiefensuche erzeugen beim Durchschreiten des Graphen einen Suchbaum, der ein Spannbaum ist (vgl. Spanning Tree bei Ethernet in STP028) Abwägung: Tiefensuche ist einfacher zu implementieren und hat weniger Speicheraufwand (braucht nur eine "besucht-Markierung" und keine Kandidatenliste), kann aber in der Praxis problematisch sein :) Beobachtung: Breitensuche findet garantiert den kürzesten Pfad vom Startpunkt zu einem gewünschten Endpunkt Abwandlung für Wegfindung: Dijkstra-Algorithmus Voraussetzung: Kanten haben auch noch ein Gewicht (analog zu einer Streckenlänge) Breitensuche merkt sich bei jedem Knoten den kürzesten Gesamtweg zu diesem Knoten beim Auswählen des nächsten Besuchskandidaten Wahl des Knotens mit dem kürzesten Gesamtweg Erweiterung zum A*-Algorithmus mittels Ergänzung um eine Heuristik, die beschreibt, wie nahe gefundene Knoten am Ziel sind (damit je nach Situation enorme Effizienzsteigerung möglich, siehe z.B. dieser Blogpost der Factorio-Entwickler) im Gespräch erwähnt: #WissPodWeihnacht 3: Das Haus vom Niko…hä?!? mit Geschichten aus der Mathematik

  • S1 · E86
    February 26 · 1 hr 29 min

    STP086: Literatur: Ein Plädoyer für schlanke Software

    Die Erfahrung, dass das Plastikgehirn gelegentlich länger für die Dinge braucht, die wir ihm aufgeben, kennen wir alle. War das früher nicht schon mal besser? Oder sollte es nicht zumindest der Vergangenheit angehören? Oder täuschen wir uns und verklären die Vergangenheit… Shownotes Anhand von "A Plea for Lean Software" (1995) von Niklaus Wirth besprechen wir zwei wesentliche Fragestellungen. Zuerst einige Vorbeobachtungen: Frage 1: Warum ist Software (bzw. Produkte im Allgemeinen) immer weniger langlebig? COBOL-Software aus den 60ern ist immer noch im Einsatz, aber React-Apps von vor 5 Jahren sind hoffnungslos obsolet siehe Vermutung, dass in der Frontend-Entwicklung Schnelllebigkeit von YouTube-Influencern getrieben wird bei COBOL/Fortran-Systemen auch regulatorische Hürden (z.B. Steuerungsoftware für Atombomben in Fortran 77, weil ein Umstieg auf neuere Versionen Tests der Software erfordern würde, aber Atomwaffentests verboten sind) vgl. Erfahrung von ttimeless: Fensterbeschläge von vor 30 Jahren noch top, aber neuere von vor 5 Jahren tw. schon abgeranzt (Geplante Obsoleszenz? Survivorship-Bias?) Wie schätzt man Qualität bei selten gekauften Produkten ab? im Gespräch erwähnt: Backblaze Drive Stats sich gegenseitig beschleunigende Marktmechanismen (Qualitätsschwund durch Sparmaßnahmen in der Produktion, Mode) passend dazu: "Ich sah neulich eine alte Episode von 'Der Preis ist heiß' aus den 80ern, die UK-Edition mit [Bruce Forsyth]. Die Preise waren Dinge wie Mikrowellen, Fernseher, Möbelstücke und so weiter. Die Preise waren weit, weit höher, als was ich je geraten hätte. Wir sind mit der Vorstellung aufgewachsen, dass eine Mikrowelle weniger als 100 Pfund kosten sollte, obwohl sie unter Berücksichtigung der Inflation mittlerweile 400 kosten sollten. Alles ist scheiße günstig geworden." These von ttimeless: mehr Leute machen mehr Zeug machen mehr Altlasten (Xyrill erhöht um eine Coding-KI-Industrie und möchte sehen) Frage 2: Warum waren Computer in den 90ern schneller? welch Ironie, dass wir uns nach der Zeit zurücksehnen, in der der Autor unseres Textes sich über verschwenderische Programmierweisen aufregt vgl. Frage im MDR: Wann kriegen wir wieder Akkulaufzeiten von einer Woche wie bei den alten Nokia-Handys? offensichtlicher Einfluss: mehr Leistung, die sich nicht als konkrete Funktion äußert (z.B. höhere Auflösung erfordert mehr Videospeicher, moderne Konnektivität ist objektiv komplexer, als nur auf einen Anruf oder eine SMS zu warten) Gegenrede: "Ich war dabei bei den meisten dieser alten Maschinen und meiner Erinnerung nach waren sie immer langsam, weswegen es ein derart unerbittliches Rennen um das Upgrade auf eine schnellere Maschine gab, und warum für eine lange Zeit Leute jedes Jahr ihren alten Computer ersetzten. [...] Dieser Topos von 'wie konnten Dinge langsamer werden, damals war alles so schnell' ist eine fehlerhafte Erinnerung" andere Perspektive aus demselben Thread: "Weil wir erweiterbare anstatt zusammensetzbarer Software schreiben. Wir liefern nicht Funktionen aus, sondern Apps. Wieviele Instruktionen braucht man, um in Maschinensprache 1+1 auszurechnen? Wieviele Instruktionen braucht man, um die Suchleiste zu öffnen, den Taschenrechner zu finden und die Berechnung auszuführen?" vgl. Freak Show 273 im Kapitel mit dem Nachruf auf Niklaus Wirth: in den 60ern vorherrschende Vorstellung unmittelbar bevorstehender Ablösung von Programmierern durch Computer, aber mehr Rechenleistung erfordert noch mehr Programmierer (vgl. Softwarekrise, für den Verweis auf kombinatorische Explosion von Software-Komplexität siehe STP070) Komplexitätsquellen laut Wirth "verbesserte Benutzerführung und Funktionalität" laut Wirth keine gute Begründung aber Wirth begründet das mittels seines eigenen extremen Fokus auf Basisfunktionalität ("Diese grundlegenden Aufgaben haben sich [... angesichts u. a. der] Ersetzung von aussagekräftigen Befehlswörtern durch hübsche Bilder [nicht geändert].") Desktop-Metapher und Skeuomorphismus waren essentiell darin, Computersoftware einem breiten Publikum näherzubringen vgl. Brooks (essentielle vs. versehentliche Komplexität), aber unterschiedliche Grenzziehungen Wirth bevorzugt ziemlich explizit "simple" statt "easy" jede Funktion, die der Kunde haben will, wird eingebaut, ob sie sich nun sinnfällig in das ursprüngliche Design einfügt oder nicht Komplexität durch Komplikationen monolithischer Systementwurf ("Jeder Kunde zahlt für alle Funktionen, aber nutzt nur wenige von ihnen.") vgl. oben "wir liefern nicht Funktionen aus, sondern Apps" Xyrill baut Systeme auch eher monolitisch, weil sich für ihn der Wartungsaufwand verringert, wenn alles in einer Codebase liegt Komplexität wird an sich als Funktionalität missverstanden: "Immer mehr scheinen die Leute Komplexität als Raffinesse zu interpretieren, was rätselhaft ist — Unverständliches sollte Argwohn erregen, nicht Bewunderung." *hust* *hust* ✨KI✨ *hust* *hust* kapitalistischer Anreiz: damit Nutzer in der eigenen Teergrube binden und Support und Beratung verkaufen gutes Design erfordert systematische Iteration auf dem ersten, offensichtlichen, überkomplizierten Entwurf vgl. Antoine de Saint-Exupéry ("Es scheint, dass Perfektion nicht dann erreicht ist, wenn nichts mehr hinzuzufügen ist, sondern wenn nichts mehr wegzunehmen ist.") aber: Zeitdruck ("akribische Ingenieursroutine zahlt sich kurzfristig nicht aus") Wirth drischt hier stark auf die Kunden ein, die ständig neuen Klimbim wollen, was etwas aus der Zeit gefallen wirkt (bzw. nur etwas deplatziert; heute sind "die Kunden" die Werbeabteilung, die noch mehr Datenspuren sammeln will) deswegen auch extrem langsame Einführung von Techniken für methodisches Arbeiten (z.B. stark typisierte Programmiersprachen): "Methodisch korrektes Design [...] ist offenbar unerwünscht, weil auf diese Weise entwickelte Produkte zu viel Zeit bis zur Markteinführung brauchen." Wirth beschwert sich, dass in den 90ern die Programmiertheorie der 70er (z.B. abstrakte Datentypen) erst langsam in Produktivumgebungen Einzug fand passend dazu kommt zurzeit die Programmiertheorie der 90er (z.B. algebraische Datentypen wie in STP072, affine Typsysteme) erst langsam in die heutigen Produktivumgebungen, aber C hält sich immer noch hartnäckig Wie heraus aus der Teergrube? Wirth bespricht sein eigenes Oberon System ursprüngliches Ziel: ein Betriebssystem inklusive Userspace, das kompakt genug ist, um als Lehrmaterial verwendet und in Lehrbüchern besprochen werden zu können extreme Konzentration auf "Grundfunktionen" (z.B. keine grafische Oberfläche, nur Textinteraktion) Implementation in einer typsicheren Programmiersprache mit Objektorientierung, um starke Modularität auf Codeebene zu ermöglichen Xyrill ist hier etwas skeptisch, dass Objektorientierte Programmierung hier einen großen Unterschied macht, aber für Wirth ist das extrem wichtig keine abgeschlossenen Programme, sondern nur Funktionsaufrufe also vmtl. kein Speicherschutz in Hardware, sondern nur durch Typsicherheit "Wenn ein Modul M eine Prozedur P anbietet, dann kann P aufgerufen werden, indem man einfach auf den Text 'M.P' zeigt, sobald er irgendwo auf dem Bildschirm erscheint, und eine Maustaste drückt" statt einer Leiste mit Icons eine einfache Textbox mit Befehlsnamen vgl. Plan 9, Smalltalk, Forth der Preis des schlanken Systems ist der Aufwand für den sauberen Entwurf Am Ende neun Lektionen für das Design schlanker Software. Wir zitieren Nummer 7: Die Reduktion von Komplexität und Größe muss in jedem Schritt das Ziel sein: im Lastenheft, im Design, und beim detaillierten Programmieren. Die Kompetenz eines Programmierers soll nach der Fähigkeit gemessen werden, einfache Lösungen zu finden, und ganz bestimmt nicht nach Produktivität, gemessen in "Anzahl Codezeilen, die pro Tag ausgeworfen werden". Produktive Programmierer tragen zum sicheren Desaster bei.

  • S1 · E85
    February 5 · 1 hr 13 min

    STP085: Barrierefreiheit im Web (Teil 3)

    Nachdem wir das eingegangene Feedback besprochen haben, starten wir zur letzten Etappe dieses überraschend ergiebigen Themas. Weder fehlt es an Anekdoten noch an vorbei fahrenden Krankenwagen und zuletzt müssen auch noch ein paar Worte über Spiele verloren werden. Shownotes siehe STP081: gemäß des neuen Barrierefreiheitsstärkungsgesetzes müssen Webseiten und Webapplikationen die AA-Kriterien der WCAG 2.1 erfüllen WCAG = Web Content Accessibility Guidelines (Webinhalte-Barrierefreiheits-Richtlinien) der Web Accessibility Initiative des W3C Kriterien sind gruppiert in 4 Grundprinzipien und darin 13 Richtlinien Kriterien gehen jeweils von A (Pflicht) über AA (Kür) bis AAA (Sahnehäubchen) in STP081 und STP083: das Grundprinzip 1 (Wahrnehmbarkeit) und 2 (Bedienbarkeit) mit insgesamt neun Richtlinien, heute der Rest zum Mitlesen: WCAG 2.2 (aktuelle Version, nur Englisch) oder WCAG 2.0 (etwas ältere Version, in offizieller deutscher Übersetzung) Grundprinzip 3: Verständlichkeit Richtlinie 10: Lesbarkeit A: Sprache der Webseite muss programmatisch auslesbar sein AA: Sprache jedes Teils der Webseite muss programmatisch auslesbar sein AAA: für ungewöhnliche Ausdrücke, Fachwörter und Abkürzungen soll eine Definition zugänglich sein; für komplizierte Texte (alles über Hauptschulniveau) soll eine Alternativform in einfacher Sprache vorliegen; Aussprachehinweise sollen zugänglich sein, sofern die Bedeutung eines geschriebenen Wortes von der Aussprache abhängt (z.B. "umfahren" vs. "umfahren") Richtlinie 11: Vorhersehbarkeit A: Bedienung von Steuerelementen soll nicht unvorhersehbar eine Seitennavigation oder dergleichen auslösen; Hilfemechanismen (inkl. Kontaktinformationen) müssen (sofern vorhanden) auf jeder Unterseite gleich funktionieren AA: Navigationsmechanismen und wiederholte Steuerelemente müssen auf jeder Unterseite gleich erscheinen und funktionieren AAA: Navigation nur aufgrund von expliziter Anforderung durch die Nutzer:in Richtlinie 12: Hilfestellung bei der Eingabe A: fehlerhafte Eingaben müssen klar hervorgehoben werden; benötigte Eingaben müssen klar als solche gekennzeichnet sein; Daten sollen nicht mehrmals abgefragt werden (beim zweiten Mal entweder automatisches Ausfüllen oder eine Option zur Datenübernahme), außer wenn Sicherheit es erfordert oder die vorliegenden Daten veraltet sind AA: bei fehlerhaften Eingaben sollen Korrekturvorschläge gegeben werden (soweit möglich; z.B. nicht, wenn Geheimniswahrung gefährdet wäre); rechtlich verbindliche Vorgänge sollen entweder umkehrbar sein oder einen separaten Bestätigungsschritt anbieten; Authentifizierung soll keine Tests für geistige Leistungsfähigkeit erfordern (z.B. für Captcha muss eine alternative Methode existieren, außer wenn der kognitive Test nur Bilderkennung oder Wiedererkennung vergangener Eingaben umfasst; Passwort-Manager-Blocker sind verboten) AAA: kontextsensitive Hilfe bei jeder Eingabe; jegliche formularbasierte Eingabe soll entweder umkehrbar sein oder einen separaten Bestätigungsschritt anbieten; Komplettverbot von Captchas ohne Alternativmethode, die keinen Test für geistige Leistungsfähigkeit umfasst Grundprinzip 4: Robustheit Richtlinie 13: Kompatibilität A: für alle Steuerelemente sind der Name und die Rolle programmatisch auslesbar (z.B. mittels ARIA (Accessible Rich Internet Applications, barrierefreie reichhaltige Internet-Anwendungen)) AA: für alle Steuerelemente sind der aktuelle Status bzw. eventuelle Statusnachrichten programmatisch auslesbar (z.B. durch Screenreader) Feedback zu STP003 Dominic schreibt Themenvorschläge, und außerdem: Vor kurzem ist mir ein Video untergekommen, das die unterschiedlichen Gatter sehr anschaulich zeigt und das ich hiermit empfehlen möchte. (Allerdings empfehle ich das Englische original denn die deutsche Synchronisation ist eine ✨KI✨-Stimme) macht weiter so und vielen Dank Feedback zu STP084 Daniel schreibt: Hallo Xyrill, hallo stell es dir in einer unbekannten Fremdsprache vor ttimeless, TL,DR: macht 'ne Folge über alternative Betriebssysteme für Smartphones Ich habe euren Call for Action aus der Episode 84 des STP gehört. Bei mir liegt aktuell das Thema Betriebssystem fürs Smartphone auf dem Tisch (dazu später mehr) und da habe ich mich gefragt, ob ihr dazu nicht eine Folge oder einen Teil einer Folge machen könnt. Xyrill sagte ja mal, er wechselt alle paar Jahre zwischen Android und iOS. ttimeless hat sich hierzu, glaube ich, noch nicht geäußert (Was mit Holz? Zwinkersmiley). Es gibt ja inzwischen einige Custom ROMs auf dem Markt und einige Projekte sind auch schon wieder eingestampft (dazu später mehr). Ich glaube, GrapheneOS wurde bei euch schon mal angesprochen, mindestens im Pentaradio. Das ist ja bekannt für seine Security Features und Einstellmöglichkeiten, hat aber den klitzekleinen Nachteil, das es nur auf einer Hardware läuft (Google Pixel). Ubuntu Touch macht anscheinend auch Fortschritte. Außerdem schon lange verfügbar sind LineageOS und /e/os. Weitere: DivestOS, CalyxOS (dazu später mehr), Pixel Experience, usw, usf. Ich finde, auch im Zuge der Di.day Initiative lohnt sich ein Blick auf dieses Thema. Auch, wenn es hier ein gewisses Skill Level, die Fähigkeit zum Verzicht und Bock auf Bugs bzw Bastelfreude braucht, um mit einem alternativen Betriebssystem auf dem Smartphone unterwegs zu sein. Jetzt kommt das "später": Ich habe mir im letzten Jahr ein Fairphone 4 angeschafft und mir CalyxOS draufgeholfen. Nur um kurz nach der Installation und Einrichtung die Nachricht von den Leutis vom Projekt zu erhalten, dass erstmal keine Updates mehr over-the-air ausgeliefert werden. Wie es mit dem Projekt weitergeht, kann ich ihrer Kommunikation leider nicht entnehmen. ¯\_(^^)_/¯ Ich brauche also bald mal ein neues Betriebssystem und ich dachte, ihr habt bestimmt was Spannendes dazu beizutragen. Sei es aus eigener Erfahrung und/oder aus eurem technikbegeisterten und technikversierten Umfeld. Der Endgegner in diesem Game ist übrigens die einzige App, die ich nicht durch FOSS ersetzen kann: die Banking-App... Es liegt in der Natur der Sache, dass ich diese App nicht wie einen Messanger oder Musikstreamingdienst wechseln kann. Ich weiß, dass euer Wissensdampfer langsam den Eisberg umschifft (Lob der Sorgfalt) und ihr Zeit für die Produktion neuer Folgen braucht. Selbst wenn dieses Thema erst in einigen Monaten rankommen sollte, freue ich mich zu hören, was ihr dazu zu sagen habt. Ansonsten noch vielen Dank für viele unterhaltsame und lehrreiche Stunden und einen Podcast, bei dem ich schon einige Folgen mehrfach gehört habe. Ganz stark. Der im Gespräch erwähnte Datenspuren-Vortrag ist "Na endlich: Linux auf dem Smartphone". Feedback zu STP081/083 Toni schreibt: Lieber Xyrill, lieber ttimeless, ich wurde heute von einem Kollegen auf euren Podcast aufmerksam gemacht. Ausschlaggebend war eure kleine Episodenreihe zum Thema Barrierefreiheit im Web. Ich bin selbst geburtsblind und schon immer mit den Hürden im Netz konfrontiert, schlussendlich hat mich das dazu geführt, dass ich im Rahmen meiner Promotion derzeit zum Thema Zugänglichmachung von interaktiven visuellen Kollaborationswerkzeugen forsche. Studiert habe ich ursprünglich Spieleentwicklung. Ihr hattet in eurem Podcast zu Wortmeldungen von Betroffenen aufgefordert. Nun ist das ja schon eine Weile her - ihr meintet im Podcast, ihr nehmt die Folge Ende August auf, das sind ja immerhin schon 4 Monate. Ich finde es super, dass ihr in eurem Podcast über die Barrierefreiheit im Web aufklärt und würde mich noch viel mehr darüber freuen, wenn sie tatsächlich auch die Mehrheit umsetzen oder zumindest die Notwendigkeit dafür einsehen würde - in der Praxis wird man bei Nachfragen tatsächlich immer eher mit Skepsis und Unwillen konfrontiert, selbst aus der eher liberalen und auch der Open-Source-Community. Zudem ist das BFSG auch leider eher ein zahnloser Wolf - es gibt zwar Richtlinien, an die sich technisch jeder halten muss, insbesondere öffentliche Dienste und Dienstleister mit einer gewissen Mindestgröße, aber wo kein Kläger, da kein Richter. Menschen, die von Barrierefreiheit betroffen sind, befinden sich statistisch eher am unteren Ende der Existenzgrenze und machen sich mehr Sorgen um ihr täglich Brot als darüber, Geld in Klageverfahren zu stecken. Und selbst wenn damit Erfolg zu verzeichnen wäre, wäre gerade für große Firmen der Verlust immer noch sehr viel geringer, als das Investment, ihre Webpräsenzen von vornherein umzurüsten. Mein Ansatz hier ist daher, Barrierefreiheit direkt schon in der Lehre mitzudenken. Darum bin ich unter Anderem an der Hochschule Anhalt tätig und versuche, meine Studierenden von vornherein darauf einzuschwören. Ich könnte vermutlich einen halben Roman dazu verfassen, und auch auf den einen oder anderen Punkt aus eurem Episoden eingehen, aber wie zielführend das ist kann ich nicht sagen. Wenn euch so etwas interessiert, könnte man dazu aber ja gern mal quatschen, oder ihr fragt nochmal nach konkreten Kommentaren, dann setze ich mich hin und mache euch eine Liste fertig ;). Bis dahin habt ihr vermutlich einen neuen Hörer dazugewonnen, je nachdem, ob ich noch einen Podcast mehr in meinen täglichen Informationswust reinquätschen kann ;). Macht weiter so, haltet die Ohren steif, und viel Erfolg und Glück im Jahr 2026.

  • S1 · E84
    January 15 · 1 hr 7 min

    STP084: Cursed Computer Iceberg Meme, Runde 3

    Mal wieder stehen uns angesichts der Merkwürdigkeit der Computertechnik die Haare zu Eisberge. Shownotes Wir setzen unsere Betrachtung des Cursed Computer Iceberg Meme aus STP042 und STP064 fort. Dieses Mal hat Xyrill sich vorgenommen, einen Pick aus jeder Ebene des Eisbergs zu besprechen. "Above the Iceberg" - Oberhalb des Eisbergs: Spectre/Meltdown Beispiel eines Seitenkanalangriffs (vgl. Besprechung von nicht-zeitkonstanten Operationen in STP041) war damals (2018) auch im Pentaradio besprochen worden und im Chaosradio Grundlage: moderne Prozessoren erzielen ihre Geschwindigkeit zu guten Teilen durch spekulative Ausführung zukünftiger Instruktionen (siehe STP011) Idee: Angreifer kann nicht auf geschützten Speicher zugreifen, aber die spekulative Ausführung weiß das nicht spekulativ ausgeführter (und dann verworfener) Befehl ist so gebaut, dass je nach dem Wert eines geschützten Bytes eine unterschiedliche Speicherseite angefasst wird dann Auslesen des Wert des Bytes durch Timing-Seitenkanal: zuletzt angefasste Speicherseite ist im Cache und schneller lesbar "On the Iceberg" - Auf dem Eisberg: Schriftarten können Schadcode enthalten Kombo mit "Middle of the Iceberg" weiter unten "Below the Water" - Unter der Wasserlinie: Magic the Gathering is Turing Complete vgl. unsere Besprechung von "aus Versehen turingvollständig" in STP042 sowie von Turingmaschinen in STP063 Kyle Hill hat dazu auch noch ein neueres Video auf seinem eigenen Kanal "Middle of the Iceberg" - Mitte des Eisbergs: Font-Hinting ist turingvollständig noch ein Fall von "aus Versehen turingvollständig" (siehe STP042) Hinting: Anpassung der Form einer Glyphe an die tatsächliche Schriftgröße in Pixeln etc., um ungewollte Rasterisierungs-Artefakte zu reduzieren (grafisches Beispiel) in TrueType: Hinting in einer VM, die durch Code in der Schriftartendatei gesteuert wird; damit Einschleusung von Schadcode möglich, wenn diese VM Schwachstellen hat Problem: heute Schriftarten nicht nur im Betriebssystem vorinstalliert, sondern auch dynamisch geladen als Webfont "Bottom of the Iceberg" - Unterseite des Eisbergs: Es gibt keine elegante Lösung für FizzBuzz "Below the Iceberg" - Unterhalb des Eisbergs: SAT-Solver werden immer schneller SAT (von engl. "satisfiability"): Erfüllbarkeitsproblem der Aussagenlogik relevant deswegen, weil man viele Probleme als SAT-Problem umformulieren kann (z.B. Sudoku, Raumplanung, Paketmanager) "Deep Water" - Im tiefen Wasser: FJCVTZS FJCTVZS = "Floating-point Javascript Convert to Signed fixed-point, rounding toward Zero" (Konvertierung eines float64 in einen int32 mit Rundung zur Null hin und Modulo 2^32 bei Überlauf) ARM ist zwar RISC (siehe STP075), aber eine spezielle Instruktion für Zahlenumwandlungen in JavaScript-Engines ist offenbar doch wertvoll "The Abyss" - Der Abgrund: Die große Adressdatei der japanischen Post eine Lektion darin, wie wichtig saubere Daten sind, und dass man auf bei der Erstellung von Dateien auf ihre Verwendung achten muss (Parallele zu Dokumentation) Es gibt weiterhin mehr zu entdecken. Wir sehen uns wieder in STP105.

  • S1 · E83
    Dec 25, 2025 · 59 min

    STP083: Barrierefreiheit im Web (Teil 2)

    Der versprochene zweite Teil ist da. Auch heute soll es darum gehen, wie eine angenehme Erfahrung im Internet und allgemein an Computern aussehen könnte. Zum Thema, ob wir alles geschafft haben, siehe Shownotes unten. Frohe Weihnachten allerseits. Shownotes siehe STP081: gemäß des neuen Barrierefreiheitsstärkungsgesetzes müssen Webseiten und Webapplikationen die AA-Kriterien der WCAG 2.1 erfüllen WCAG = Web Content Accessibility Guidelines (Webinhalte-Barrierefreiheits-Richtlinien) der Web Accessibility Initiative des W3C Kriterien sind gruppiert in 4 Grundprinzipien und darin 13 Richtlinien Kriterien gehen jeweils von A (Pflicht) über AA (Kür) bis AAA (Sahnehäubchen) in STP081: das Grundprinzip 1 (Wahrnehmbarkeit) mit insgesamt vier Richtlinien, heute der Rest zum Mitlesen: WCAG 2.2 (aktuelle Version, nur Englisch) oder WCAG 2.0 (etwas ältere Version, in offizieller deutscher Übersetzung) Grundprinzip 2: Bedienbarkeit Richtlinie 5: Zugänglichkeit per Tastatur A: alle Aktionen per Tastatur ansteuerbar, die nicht eine genaue geometrische Ansteuerung erfordern (z.B. Zeichenfläche in einem Zeichenprogramm); kein Steuerelement kann den Tastaturfokus so fangen, dass man den Fokus nur mit einer anderweitigen Aktion (z.B. Mausklick) brechen kann; etc. AAA: ausnahmslos alle Aktionen per Tastatur ansteuerbar Richtlinie 6: Ausreichend Zeit A: wenn Interaktionen ein Zeitlimit haben, muss das Limit (wann immer möglich) in irgendeiner Form umgehbar oder zurücksetzbar sein (Aufgaben sollen abschließbar sein, ohne dass ein Zeitlimit plötzlich den Fortschritt zunichte macht); jegliches automatische Bewegen/Scrollen/Blinken/Aktualisieren muss abschaltbar sein AAA: absolut keine Zeitlimits für Interaktionen; bei Relogin aufgrund abgelaufener Sitzung darf kein Fortschritt verloren gehen; Benutzer müssen jederzeit über laufende Zeitlimits informiert sein, die kürzer als 20 Stunden sind Richtlinie 7: Keine Anfälle A: Inhalte, die mehr als 3x pro Sekunde blinken, müssen eine Intensität unter den Grenzwerten für Epilepsierisiko liegen AAA: gar kein Blinken schneller als 3x pro Sekunde; Animationen infolge von Benutzerinteraktionen müssen abschaltbar sein Richtlinie 8: Navigierbarkeit A: sinnvolle Titel auf jeder Seite; über mehrere Seiten wiederholte Informationen sind überspringbar; Steuerelemente haben eine sinnvolle Fokusreihenfolge; der Zweck von Links soll soweit wie möglich aus dem Linktext allein erkennbar sein (z.B. nicht "[Hier klicken], um den Kauf abzuschließen") AA: statische Seiten sollen auf mehrere Wege auffindbar sein; Seiten sind mittels Teilüberschriften und Labels sinnvoll strukturiert; Tastaturfokus auf Steuerelementen soll klar erkennbar sein; Steuerelemente mit Fokus sollen nie komplett verdeckt sein (z.B. durch ein danebenliegendes Ausklappmenü); etc. AAA: aktueller Ort des Nutzers innerhalb einer Webseitenstruktur soll klar erkennbar sein (z.B. "Sie sind hier: [Start] > [Blog] > [Archiv] > Name des aktuellen Artikels"); etc. Richtlinie 9: Alternative Eingabemethoden A: Webseiten/-applikationen, die Mehrpunkt-Interaktion erlauben ("Touch-Gesten"), sollen auch eine Alternative für zeigerbasierte Einzelpunkt-Interaktion erlauben; Aktionen infolge fehlerhaften Runterdrückens der Maustaste sollen abwendbar oder umkehrbar sein; Interaktion durch Bewegungssteuerung soll auch durch Steuerelemente ersetzbar sein sowie gegen Fehlaktivierung resistent sein; etc. AA: Klickflächen müssen mindestens 24x24 CSS-Pixel groß sein (vgl. Fitts' Gesetz) AAA: Klickflächen müssen mindestens 44x44 CSS-Pixel groß sein; alternative Eingabemethoden sollen beliebig gleichzeitig nutzbar sein (ohne explizites Umschalten) im Gespräch erwähnt: Zenons Paradoxon von Achilles und der Schildkröte, The Topological Problem with Voting (Video) In Teil 3 dieser Serie folgen noch Grundprinzip 3 (Verständlichkeit) und 4 (Robustheit).

  • S1 · E82
    Dec 4, 2025 · 1 hr 41 min

    STP082: Literatur: Vom Mythos des Mann-Monats, Teil 3

    Als letzten Streich in der Besprechung dieses Werkes hört ihr einen Mitschnitt von den Datenspuren von 2025-09-19; und da wir leider nicht den ganzen Rest des Buches in unsere Bühnenzeit bekommen haben, auch noch den Rest in der gewohnten Form. Applaus für den Presenter! Shownotes Fortsetzung aus STP068 und STP074. Wir lesen weiterhin die englische Erstausgabe von 1975, die im Internet Archive digitalisiert wurde. Erneut als Vorbemerkung: Aus Quellentreue sagen wir "Mann-Monat" statt "Person-Monat". Kurzzusammenfassung der bisherigen Folgen Für die Zuschauer im Saal, die die vergangenen Folgen nicht gehört haben. Das übergreifende Motiv in dieser ersten Hälfte des Buches ist, wie sich die Arbeit in großen Teams von kleinen Teams unterscheidet. Die Teergrube So wie man in der Teergrube erst gefangen ist, wenn alle Beine drinstecken, so resultiert die Trägheit von Software-Entwicklung aus einem Zusammenspiel mehrerer Faktoren. Ein Programm zu schreiben, ist einfach. Aber die Produktisierung erfordert viel mehr Aufwand: für Generalisierung, Testabdeckung, Dokumentation und fortlaufende Wartung. Außerdem muss sich das Programm in ein größeres System einfügen. Vom Programm zum Programmsystemprodukt erhöht sich der Aufwand um ungefähr eine ganze Größenordnung. Vom Mythos des Mann-Monats Konventionelle Planungsmethoden funktionieren nur, wenn Personen und Monate austauschbar sind. Das beachtet jedoch weder die unterschiedlichen Kompetenzniveaus verschiedener Teammitglieder noch den zusätzlichen Zeitaufwand durch Kommunikation innerhalb des Teams sowie zwischen Teams. Da Programmierer aber schlecht im Schätzen von Zeitaufwand sind, wird in der Praxis der Zeitplan oft an den Bedürfnissen der Kunden ausgerichtet, nicht an den technischen Randbedingungen. Wenn dann das Kind in den Brunnen gefallen ist, tritt das Brooks'sche Gesetz in Kraft: "Das Hinzufügen weiteren Personals zu einem verspäteten Softwareprojekt verspätet es weiter." Das OP-Team Um die Kommunikationskosten zu verringern, stellt Brooks ein Modell für kleinere Teams vor, die in Analogie zu einem OP-Team organisiert sind, in dem immer nur einer auf einmal die eigentliche Programmierarbeit leistet und alle anderen nur zuarbeiten. Die genaue Beschreibung ist sicherlich überholt: Heutzutage braucht man zum Beispiel keinen Schreiber mehr, der Lochkarten sortiert. Aber vielleicht haben wir auch etwas verloren, als wir Sekretärsrollen ersetzt haben dadurch, dass jetzt die rare Expertin Termine im Outlook schubsen und Präsentationsfolien zusammenklicken muss. Aristokratie, Demokratie und System-Design Die Kathedrale von Reims wurde von acht Generationen von Baumeistern errichtet, weist aber trotzdem eine beachtliche gestalterische Kohärenz auf, weil die nachfolgenden Generationen das ursprüngliche Design respektiert haben. Daraus muss aber nicht folgen, dass ein einzelner Architekt alle Entscheidungen trifft und die Erbauer nur stupide die Pläne umsetzen. Auch auf der Umsetzungsebene gibt es viele interessante Designentscheidungen zu treffen; und ein guter Architekt hört auch auf seine Erbauer, wenn es um Fragen von Praktikabilität geht. Das Problem des zweiten Systems In diesem Dialog zwischen Architekt und Erbauer stellen sich also oftmals Ideen des Architekten als unpraktikabel heraus und werden verworfen. Doch wenn das erste System erfolgreich war, gewinnt der Architekt an Prestige und Erfahrung, die dazu verleiten kann, beim nächsten Mal alle Sachzwänge zu ignorieren. Ein weiteres klassisches Diktum von Brooks ist deswegen: "Dieses zweite ist das gefährlichste System, dass man jemals entwirft." Weitergabe von Informationen Damit ein Entwurf von 10 Architekt:innen von 1000 Mitarbeiter:innen und nochmal deutlich mehr Nutzer:innen verstanden wird, braucht es gute Dokumentation: Handbücher für Benutzer, und Architekturpläne für Erbauer. Brooks schlägt hier einiges vor, was heute in der Industrie gelebte Praxis ist (oder zumindest sein sollte), zum Beispiel maschinenlesbare Spezifikation von Schnittstellen und automatisierte Tests zur Überprüfung der Kompatibilität. Sein Ruf nach sorgfältiger Pro/Kontra-Abwägung zwischen mehreren möglichen Design-Optionen verhallt im Zeitalter agiler Softwareentwicklung jedoch oftmals ungehört. Warum ist der Turm zu Babel gefallen? Offensichtlich ist ineffektive Kommunikation einer der wesentlichen Gründe dafür, dass Software-Großprojekte scheitern oder erst mit deutlicher Verspätung liefern. Somit stellt sich die Frage nach der optimalen Teamstruktur in einer Software-Entwicklungsabteilung. Brooks hält eine baumförmige Struktur für unausweichlich, damit Entscheidungskompetenzen klar geregelt sind. In jedem Entwicklungsteam sollte es sollte es neben einem Architekten (dem Chefentwickler des Teams) auch einen Produzenten geben, der sich um die Kommunikation mit anderen Teams kümmert. Da eine Personalunion zwischen beiden Rollen nicht skaliert, muss entweder der Architekt der Chef des Produzenten sein: Dies passt aber nicht zu den separaten Management-Karrieren in den großen Firmen. Oder der Produzent ist der Chef des Architekten: Dies kann aber nur funktionieren, wenn der Produzent die technische Autorität des Architekten akzeptiert. Kapitel 8: "Calling the Shot" "Calling the Shot" hier im Baseball-Sinne: vorher ansagen, wo der Ball nach dem Schlag landet Wie lange wird eine System-Programmierungsaufgabe dauern? Wieviel Aufwand ist nötig? Wie schätzt man das? Problem: Code schreiben alleine ist noch einigermaßen abschätzbar, macht aber nur einen kleinen Teil (vllt. ein Sechstel) des Gesamtaufwandes aus Aufwand steigt exponentiell mit der Komplexität des Programmiersystems, weil Interaktionen zwischen verschiedenen Teilen des Systems beachtet werden müssen und Kompromisse im Design erfordern (vgl. Kapitel 1) und dann zusätzlicher Overhead, sobald Kommunikation zwischen mehreren Teammitgliedern erforderlich ist (vgl. Kapitel 2) Brooks fasst dann Erkenntnisse aus mehreren quantitativen Studien zusammen; Highlights: Geschwindigkeitsschätzungen waren zu Beginn immer ziemlich akkurat, aber im Verlauf des Projektes wird mit zunehmender Komplexität alles immer träger Aufwand scheint am stärksten von der Gesamtmenge an Code abzuhängen (sprich: 1000 Zeilen Code sind ähnlicher Aufwand, unabhängig von der Sprache) -> Überleitung in das nächste Kapitel Kapitel 9: Zehn Pfund in einem Fünf-Pfund-Sack wenn Code kein Wert an sich, sondern eine Verbindlichkeit ist, wie kann man Code reduzieren? Hochsprachen -> vgl. "No Silver Bullet" und intrinsiche vs. versehentliche Komplexität ("essential vs. accidental complexity"; besprochen im Pentaradio vom Dezember 2022) Xyrill sieht einen Bezug zum Hype um Coding-KI und die damit verbundenen Werbeversprechen Brooks zieht eine Parallele zu Hardware-Entwurf: "Weil die Größe ein wichtiger Teil der Benutzerkosten eines Programmiersystem-Produktes ist, muss der Erbauer Größenziele setzen, die Größe im Auge behalten, und Techniken zur Größenreduktion ersinnen; genau so, wie ein Hardware-Erbauer Komponentenzahlziele setzt, die Komponentenzahl im Auge behält, und Techniken zur Reduktion der Komponentenzahl ersinnt. Wie jede Art von Kosten ist Größe an sich nicht schlecht, aber überflüssige Größe ist es." vgl. Kapitel 1 (siehe STP068), wo bereits ein vordefiniertes Ressourcenbudget für jedes Teilprogramm gefordert wurde heute (leider?) nicht mehr en vogue; Speicher ist zu günstig geworden "Repräsentation ist die Essenz des Programmierens": Brooks hält den Entwurf passender Datenstrukturen für sehr viel relevanter als die Auswahl passender Algorithmen Xyrill stimmt offensichtlicherweise zu, siehe STP071/072 "Zeig mir deine Flussdiagramme ohne die [Datenbank-]Tabellen, und ich werde verwirrt bleiben. Zeig mir deine Tabellen, und ich werde die Flussdiagramme wahrscheinlich nicht brauchen; sie werden offensichtlich sein." Xyrill vermutet, dass hierher seine tiefe Abneigung gegen Prozess-Designer rührt Kapitel 10: Die dokumentarische Hypothese Die Hypothese: Verborgen in einem riesigen Papierhaufen verborgen, werden eine kleine Zahl von Dokumenten zu kritischen Angelpunkten, um die sich das Management eines jeden Projektes dreht. Dies sind die zentralen Werkzeuge eines Managers. "Auf einen neuen Manager, der gerade aus dem Handwerk gewechselt ist, erscheint der meiste Papierkram als vollständiges Ärgernis, als unnütze Ablenkung, und eine weiße Flut, die droht, ihn zu umspülen. Und in der Tat sind die meisten dieser Dokumente genau das." doch einige Dokumente sind essentiell und das wesentliche Arbeitsergebnis des Managers Mindestsatz laut Brooks: Zielsetzungen/Spezifikationen, Zeitplan, Budget, Ressourcenzuteilung, Personalzuteilung (letzteres vgl. Conway's Gesetz: "Organisationen, die Systeme entwerfen, sind gezwungen, Systeme hervorzubringen, die die Kommunikationsstruktur dieser Organisation kopieren.") wesentliche Funktionen von Dokumentation für den Manager: Festhalten von Entscheidungen: Aufschreiben legt Widersprüche, Denkfehler und -lücken offen Kommunizieren von Entscheidungen: Manager sind die meiste Zeit Kommunikatoren und nur relativ selten tatsächlich Entscheider Erinnern von Entscheidungen: klare Dokumentation einer Entscheidung mit Begründung ermöglicht spätere Rezension und Entscheidung, wann eine Richtungsänderung angebracht ist Kapitel 11: Plane damit, eines wegzuwerfen ("Plan to Throw One Away") Analogie zu Pilotanlagen in der Chemietechnik: beim Übergang von Laborprozessen zu Fabrikproduktion im großen Maßstab sind Skalierungsprobleme und methodische Fragen zu lösen, sodass man nicht sofort die Fabrikanlage in der finalen Größe bauen kann "Plane damit, eines wegzuwerfen. Du wirst es sowieso tun." Programmierer waren zu Brooks' Zeiten damit beschäftigt, die Lektion zu lernen, und sind es heute immer noch damit im Zusammenhang: Wie geht man mit Veränderungen der Umstände um? Wieviel Veränderung der Umstände ist man bereit, zu akzeptieren? These: Unwillen zur Dokumentation ist Unwillen, sich auf eine Entscheidung festzulegen, von der man schon weiß, dass sie immer nur vorläufig sein kann bis hin zu Teamstruktur: "In einem großen Projekt muss der Manager zwei oder drei Topprogrammierer als technische Kavallerie vorhalten, die zu Rettung galoppieren können, wo immer der Kampf am schwierigsten ist." (Xyrill ist sich nicht sicher, ob er da mitgeht) Software-Maintenance laut Brooks besteht hauptsächlich aus "Änderungen, die Designfehler beheben" Xyrill stimmt nur im Teil zu: der meiste Aufwand bei Maintenance heutzutage ist "Bit Rot" (Umgang mit der stetig fortschreitenden Fäulnis im Ökosystem), also nur indirekt Behebung von Designfehlern jede Behebung eines Fehlers kann aber auch neue Fehler erzeugen (sowohl auf handwerklicher Ebene als auch auf Design-Ebene) automatisierte Tests helfen, sofern sie eine hinreichend gute Abdeckung erzielen und nicht so aufwändig sind, dass sie den Arbeitsprozess behindern trotzdem: Programme werden im Verlauf ihres Lebenszyklus immer komplexer, wodurch die Rate von Folgefehlern steigt der letzte Satz des Kapitels war bereits im Juni im Pentaradio zitiert: "Das Erbauen eines Programms ist ein entropieverringernder Prozess […] Die Wartung eines Programms ist ein entropieerhöhender Prozess, und selbst die gescheiteste Umsetzung kann das unausweichliche Absacken des Systems in unreparierbare Obsoleszenz höchstens verzögern." Kapitel 12: Scharfe Werkzeuge Programmierer sind eine der wenigen Berufsstände, die ihre eigenen Werkzeuge bauen da Effizienz aus der Qualität des Instrumentariums folgt, sollen Softwareentwicklungs-Manager Ressourcen abstellen für "Werkzeugmacher" aber: heute anderer Fokus als damals; weniger Bedarf nach z.B. Debugging-Werkzeugen (das bringt die Programmiersprache mit) und mehr Bedarf nach z.B. CI/CD oder Linting Brooks bespricht dann Strategien, die nicht auf den allgemeinen Fall übertragbar sind Rationierung der Rechenzeit auf raren Mainframes: heute haben wir überproportionierte PCs für jeden Entwickler, sowie elastische Cloud-Infrastruktur für alles, was da nicht heraufpasst Umgang mit Prerelease-Hardware: betrifft die allermeisten großen Software-Projekte nicht (aber siehe dieser Vortrag von einem AMD-Chipdesigner) Brooks stellt als offensichtlich wertvolles Werkzeug Hochsprachen auf eine Stufe mit interaktiver Programmierung "Ich bin überzeugt, dass nur Schwerfälligkeit und Faulheit die universelle Annahme dieser Werkzeuge aufhalten; die technischen Schwierigkeiten sind nicht länger valide Ausreden." Vorteile von Hochsprachen: erhöhte Produktivität (aufgrund weniger Code; siehe Kapitel 8/9), weniger Programmierfehler (nicht nur aufgrund weniger Code, sondern weil ganze Fehlerklassen eliminiert werden) bei interaktiver Programmierung Bezug zu MIT Multics (dem Vorgänger von AT&T Unix): Xyrill hatte hier zuerst an Systeme wie Smalltalk gedacht, aber offenbar ist "interaktiv" hier das Gegenwort zu "Batch Processing" Kapitel 13: Das Ganze und die Teile Wie verhindert man Probleme beim Zusammenfügen mehrerer Teilprogramme zu einem Gesamtsystem? Brooks enumeriert hier viele bereits erwähnte Sachen: strukturierte Programmierung in Hochsprachen, Debugging (entweder interaktiv auf der Zielmaschine, oder post-mortem mit einem Speicherabbild), Tests (sowohl für Einzelkomponenten als auch das Gesamtsystem) Missverständnisse bzw. Unklarheiten in der Spezifikation: siehe Kapitel 4-6 für Prozesse zum Erhalt der konzeptionellen Integrität des Gesamtsystems Xyrill beobachtet, dass das Schreiben der Spezifikation oftmals mehr Konzentration erfordert als das Schreiben des Code (hohe Entscheidungsdichte, dichtes Konsequenzgeflecht) Brooks empfiehlt einen Ansatz nach Niklaus Wirth: "Programmentwicklung durch schrittweises Verfeinern" mit verschiedenen Stufen von je nach Stufe möglichst groben Designs, die dann jeweils durch die nächste Stufe verfeinert werden Probleme beim Verfeinern stellen dann evtl. die Designfehler auf der gröberen Ebene bloß -> damit der Versuchung entgehen, ein schlechtes Grunddesign mit immer mehr Epizyklen zuzukleistern Empfehlung: klare Markierungen, wenn zum Zwecke der Fehlerbehebung der dokumentierte Zustand des Systems manipuliert wird Brooks beschreibt Verkabelung gemäß Plan mit gelben Kabeln und manuelle Änderungen mit lilanen Kabeln, damit diese ins Auge stechen und dann beim nächsten Update des Kabelplans berücksichtigt werden in Software nicht so sehr formalisiert, wie es sein sollte (am ehesten in Form von Systemen, die manuelle Änderungen am Produktivsystem unterbinden) weitere Empfehlungen: immer eine Komponente nach der anderen hinzufügen, nicht mehrere auf einmal Aktualisierungen nicht ständig einspielen, sondern nur ab und zu, damit man zwischendurch den stabilen Zustand des Systems beobachten kann Kapitel 14: Wie man eine Katastrophe ausbrütet ("Hatching a Catastrophe") Zeitpläne scheitern meist nicht durch ein großes Hindernis (auf welches mit einer großen Anstrengung reagiert würde), sondern durch eine Anhäufung kleiner Hindernisse vgl. politische Reaktion auf Versagen: Einsturz einer einzelnen Brücke mobilisiert sofort Unterstützung, aber schleichender Verfall aller Brücken ist alternativlos Tod durch tausend Schnitte: heute ist der Chefentwickler krank, morgen ist eine Festplatte auf dem Datenbankserver kaputt, übermorgen verspätet sich der Hardwaretest aufgrund Problemen in der Lieferkette Erkennen von Verspätungen erfordert einen festen Zeitplan mit spezifischen Meilensteinen Gegenbeispiel: "Implementation 90% fertig" stimmt so gut wie immer :) "Chronisches Überziehen des Zeitplans ist ein Teammoral-Killer." "Aber die anderen sind auch zu spät dran." trotzdem ist es ratsam, sich selber ranzuhalten, damit man nicht auf dem kritischen Pfad landet und dann das ganze Großprojekt ins Stocken bringt Manager sollten den kritischen Pfad kennen, damit sie rechtzeitig wissen, wo ihre Aufmerksamkeit am wertvollsten ist Kapitel 15: Das andere Gesicht "Ein Computerprogramm ist eine Nachricht des Menschen an die Maschine. [...] Aber ein geschriebenes Programm hat ein anderes Gesicht, dasjenige, dass seine Geschichte dem menschlichen Benutzer erzählt." selbst für Programme für den eigenen Gebrauch, damit man sich in einem Jahr noch daran erinnert, was das Programm tut Brooks möchte, dass Dokumentation aus drei Teilen besteht wie man ein Programm verwendet (klar) wie man dem Programm glaubt (Testfälle zum Ausprobieren) wie man das Programm verändert (Dokumentation über die interne Struktur, das Dateilayout, verwendete Algorithmen und Datenstrukturen) Brooks findet Strukturdiagramme super, und Flowcharts scheiße: man solle lieber äquivalenten (Pseudo-)Code hinschreiben Xyrill stimmt zu: die meisten Flowcharts aus der Praxis sind abgrundtief hässlich und unlesbar chaotisch Ergebnis: der Code sollte einfach selbstdokumentierend sein bzw. seine Dokumentation inline enthalten (vgl. Donald Knuth und "Literate Programming") offensichtlich ist das alles aus der Zeit, bevor Software ein einzeln verkauftes Produkt war im Gespräch erwähnt: The Architecture of Open Source Applications; ein Buch darüber, guten Open-Source-Code zu lesen und zu durchdringen Epilog "Die Teergrube der Software-Entwicklung wird noch eine ganze Weile klebrig bleiben. Man kann davon ausgehen, dass die Menschheit auch weiterhin Systeme in Angriff nehmen wird, die gerade so innerhalb oder gerade so außerhalb des Möglichen liegen; und Softwaresysteme sind vielleicht die vertracktesten und komplexesten aller menschlichen Schöpfungen. Das Verwalten dieses komplexen Handwerks wird von uns fordern: den bestmöglichen Einsatz neuer Sprachen und Systeme, die optimale Anwendung bewährter Methoden des Ingenieurmanagements, großzügige Mengen gesunden Menschenverstandes, und die gottgegebene Demut, die eigene Fehlbarkeit und Beschränkungen zu erkennen." Podcast-Empfehlungen Gilda con Arne – Der Politik-Podcast Dlf Doku Serien einige Trailer für Dokus Tech Bro Topia Rechtsextreme vor Gericht Neuland Die Geschichte geht weiter – Victor Klemperers Tagebücher 1918-1958

  • S1 · E81
    Nov 13, 2025 · 1 hr 4 min

    STP081: Barrierefreiheit im Web (Teil 1)

    Es gibt Menschen, die körperliche oder mentale Einschränkungen haben. Für diese Menschen könnte unsere Welt angenehmer gestaltet werden. Welche Vorteile auch nicht behinderte Menschen aus entsprechenden Maßnahmen ziehen und was diese Maßnahmen sind, darum soll es heute gehen. Und an einem anderen Tag auch. Shownotes seit 28. Juni 2025 gilt das Barrierefreiheitsstärkungsgesetz als nationale Umsetzung der EU-Richtlinie 2019/882 über die Barrierefreiheitsanforderungen für Produkte und Dienstleistungen gilt insbesondere auch für alle digitalen Dienstleistungen (Webseiten, Apps, Ticketautomaten, etc.) Leitmotiv heute: Ist das nur was für Menschen mit Behinderungen? Webseiten und Webapplikationen müssen die AA-Kriterien der WCAG 2.1 erfüllen WCAG = Web Content Accessibility Guidelines (Webinhalte-Barrierefreiheits-Richtlinien) der Web Accessibility Initiative des W3C WCAG 2.2 (aktuelle Version von 2024) enthält eine Reihe von Kriterien, gruppiert in 4 Grundprinzipien und darin 13 Richtlinien Kriterien gehen jeweils von A (Pflicht) über AA (Kür) bis AAA (Sahnehäubchen) zum Mitlesen: WCAG 2.2 (aktuelle Version, nur Englisch) oder WCAG 2.0 (etwas ältere Version, in offizieller deutscher Übersetzung) Grundprinzip 1: Wahrnehmbarkeit Richtlinie 1: Textalternativen A: Textalternativen für alle Nicht-Text-Inhalte Richtlinie 2: Alternativen für zeitbasierte Medien A: Audiobeschreibung oder Alternativdarstellung für voraufgezeichnete Bewegtbilder, Untertitel für voraufgezeichnete Videos mit Ton AA: Untertitel für Live-Videos etc. AAA: Gebärdenübersetzung für Sprache in Audio/Video etc. Richtlinie 3: Anpassbarkeit A: Struktur und Beziehungen in dargestellter Information sollen programmatisch auslesbar sein (z.B. in HTML Strukturierung anhand semantisch aufgeladener Tags wie <main>, <nav>, <aside>, <section>); Darstellung soll in korrekter Lesereihenfolge erfolgen; Struktur der Information soll nicht nur aus sensorischen Charakteristika wie Form, Farbe, visueller Anordnung oder Klängen hervorgehen AA: Inhalte sollen sowohl in Hochformat als auch Querformat funktionieren; Eingabefelder sollen programmatisch als solche erkennbar sein AAA: alle Steuer- und Inhaltselemente sollen programmatisch auslesbar sein im Gespräch erwähnt: Rot-Grun-Sehschwäche Richtlinie 4: Unterscheidbarkeit A: Farbe nicht als einziges Unterscheidungsmerkmal (z.B. zwischen guten und schlechten Optionen); Abspielen von Audioinhalten soll durch den Nutzer kontrollierbar sein AA: Text- und Hintergrundfarben sollen ein Kontrastverhältnis von mindestens 4.5:1 aufweisen (außerdem 3:1 für aktive Steuerelemente); Text soll ohne Spezialwerkzeuge um bis zu 200% vergrößerbar sein; Inhalte sollen unabhängig vom Bildschirmformat ohne exzessives Scrolling erreichbar sein; etc. AAA: Kontrastverhältnis für Text mindestens 7:1; Audio mit Sprache soll geringe Hintergrundgeräusche aufweisen; Text soll mit kurzen Zeilenlängen und mindestens anderthalbfachem Zeilenabstand dargestellt werden; reiner Text soll nicht als Bilddatei ausgespielt werden; etc.

  • S1 · E80
    Oct 23, 2025 · 38 min

    STP080: Common Weakness Enumeration (Teil 2)

    Im zweiten Teil zu üblichen Schwachstellen hören wir neben einigen Querverweisen auch Xyrills Meinung zu seiner favorisierten Verwundbarkeit. Shownotes Platz 9: CWE-862; fehlende Autorisierung siehe Besprechung von Authentifizierung und Autorisierung in STP039 Lösung: Just do it! :) passend dazu Platz 14 und 18: CWE-287 und CWE-863; fehlerhafte Authentifizierung bzw. Autorisierung außerdem Platz 15: CWE-269; unzureichende Privilegienkontrolle als Sonderfall Platz 25: CWE-306; fehlende Authentifizierung an kritischer Stelle daraus folgend Platz 17: CWE-200; Preisgabe sensitiver Informationen an nicht Zugriffsberechtigte Platz 10: CWE-434; Unbeschränktes Hochladen von Dateien des falschen Typs und dadurch z.B. Einschleusung von Schadcode (Xyrill fühlt sich an den "OpenOffice kann dienstags nicht drucken"-Bug erinnert) Lösung: nur bekannte Formate akzeptieren passend dazu Platz 16: CWE-502; Deserialisieren unvertrauenswürdiger Daten Lösung: unbekannte Daten mit sicheren Parsern validieren Platz 21: CWE-476; Zugriff auf Nullzeiger besprochen in STP045 Platz 22: CWE-798; Zugriff mit hartkodierten Anmeldedaten In wieviele Plasterouter kommt man wohl immer noch mit Username admin und Passwort letmein rein? :) tatsächlich auch bei Enterprise-Hardware oftmals Standardpasswörter voreingestellt, die dann beim Einrichten (versehentlich?) nicht geändert werden Platz 23: CWE-190; Ganzzahlüberlauf ("Integer Overflow or Wraparound") besprochen in STP003 (Überlauf in Logikgattern) und STP037 (berühmte Überlauffehler) Platz 24: CWE-400; unkontrollierter Ressourcenverbrauch Rückbezug zu STP079 (Komplexitätsattacke in Hashmaps) außerdem noch Xyrills Favorit: CWE-655; unzureichende psychologische Akzeptabilität :)

  • S1 · E79
    Oct 2, 2025 · 1 hr 2 min

    STP079: Feld von Feldern

    Nach einem kurzen Feedback gehen wir diesmal zu Karten… nein, Abbildungen über. Das ist am Anfang kein Problem. Nur wenn die Eimer für Streuwertfunktionen kleiner werden, hat ttimeless etwas Schwierigkeiten. Shownotes Rückbezug STP077: Liste von Listen verschiedene Datenstrukturen implementieren dasselbe Datenformat mit unterschiedlichen Laufzeitcharakteristiken heute analog dazu Besprechung von assoziativen Datenfeldern Rückbezug STP072: assoziative Datenfelder (wir sagen hier "Maps"; heißt je nach Programmiersprache auch "Objekt", "Dictionary", etc.) eine Sammlung von Wertepaaren mit jeweils einem eindeutigen Schlüssel ("Key") und einem zugeordneten Wert ("Value") z.B. Wörterbuch: Schlüssel ist das Lemma, Wert ist die Definition z.B. Verzeichnis im Dateisystem: Schlüssel ist der Dateiname, Wert ist die Datei (bzw. das Unterverzeichnis) praktisches Beispiel: Wörter zählen es geht hier nur um Wertepaare, die aktiv im Speicher vorliegen, nicht um berechnete Abbildungen (Gegenbeispiel: Suchmaschine bildet von Suchanfrage auf Ergebnisseite ab) Ansatz 1: "Sammlung von Wertepaaren" als Liste umsetzen sofern unsortiert, ist die algorithmische Komplexität für die meisten Operationen sehr schlecht z.B. Suchen nach einem bestimmten Schlüssel in linearer Zeit (O(n)), wenn man die Liste von vorne nach hinten durchgehen muss z.B. Einfügen eines neuen Schlüssels auch nur in linearer Zeit, weil man einen evtl. existierenden Eintrag mit demselben Schlüssel finden und ersetzen praktikable Umsetzung unter Verwendung einer sortierten Liste, um bestimmte Schlüssel schnell aufzufinden meistens mittels eines balancierten Baums, z.B. in Rust BTreeMap oder in C++ std::map Problem: Schlüssel müssen sortierbar sein (Beispiel: Strings, Ganzzahlen; Gegenbeispiel: komplexe Zahlen, Fließkommazahlen, ungeordnete Mengen) Problem: auch bei sortierbaren Schlüsseln können Vergleiche teuer sein Wie können wir die Vergleiche günstiger machen? Ansatz 2: Vorsortierung anhand von Streuwertfunktionen (Hashes) Idee: bei Suche nach einem bestimmten Schlüssel wird ein Hash des Schlüssels ermittelt (in Größenordnung einer kleinen Ganzzahl, z.B. 4 oder 8 Byte; nicht ein kryptografisch starker Hash wie SHA-2 mit 28-64 Bytes); damit schnelle Vergleiche möglich -> Hashtabelle Strategie 1: Gruppierung der Wertepaare in "Buckets" anhand der ersten K Bits des Hash-Wertes des Schlüssels K richtet sich nach der Gesamtanzahl an Wertepaaren (z.B. für 50 Elemente könnte man K = 5 oder 6 und damit 2^K = 32 oder 64 Buckets wählen) innerhalb der Buckets einfache Listen von Wertepaaren, die in diesen Bucket fallen; idealerweise nur ein Eintrag pro Bucket durch dynamisches Anpassen der Bucket-Anzahl Abwägung zwischen Speicheraufwand für evtl. leere Buckets einerseits und Zeitaufwand für Durchsuchen übervoller Buckets andererseits Strategie 2: wie 1, aber jeder Bucket kann maximal ein Element aufnehmen bei Kollisionen strategisches Ausweichen auf andere Buckets in einem systematischen Muster, bis ein freier Platz gefunden wird große Variation von Implementationsstrategien für dieses "strategische Ausweichen" Vorwärtsbezug zu STP080: Komplexitätsattacke auf Hashmaps (eine Instanz von CWE-400) Problem, wenn Hashmap mit nutzerdefinierten Daten gefüllt wird: Angreifer könnte Daten so wählen, dass sie alle im selben Bucket landen wollen damit extrem hohe Rechenlast durch ständige Kollisionen Lösung: Durchmischen des Hash mittels prozessinterner Geheimzahl (siehe STP044 zu Zufallszahlen) Feedback zu STP065 Mole schreibt: In STP065 vermutest du, dass der Ethernet-Port wegen Authentifizierung abgeschafft wurde. "Beim WLAN muss man sich authentifizieren, beim Ethernet kann man sich einfach anstecken und lossurfen." Das ist so natürlich nicht richtig. Im Enterprise-Umfeld gibt es für sowas 802.1x. Das wird übrigens auch beim WLAN zur Authentifizierung mit einem RADIUS-Server benutzt. Außerdem gibt es da SNMP-Traps. Da schaltet dann der Port ab und der Admin bekommt eine Nachricht, wenn die falsche MAC antwortet. Das gab es schon lange vor WLAN. Nächstes Problem: Du erklärst, das die NUCs vom VOC für das Streaming zuständig sind. Das ist so auch nicht richtig. Die machen nur das Encoding in die Subformate, wenn der Talk schon geschnitten ist. Für das Streaming sind die Cubes, ordentliche PCs mit extrem teuren Spezial-SDI-Encoding-Karten. Die Kisten brauchen auch echt Leistung, weil die das live machen.

  • S1 · E78
    Sep 11, 2025 · 1 hr 4 min

    STP078: Common Weakness Enumeration (Teil 1)

    Nachdem wir kurz über Alex' Feedback gesprochen haben, soll es heute mal wieder um Sicherheit gehen; diesmal speziell darum, was Personen die Software schreiben beachten sollten, um die bekantesten Fallstricke sicher zu umgehen. Shownotes Rückbezug STP049: CVE-Datenbank für bekannte Sicherheitslücken in bestimmten Programmen (z.B. Heartbleed ist CVE-2014-0160) betrieben von dem privaten Forschungsinstitut Mitre Corporation auf Basis von Fördermitteln der US-Regierung April 2025: kurzzeitige Verwirrung nach Aussetzen des Fördervertrages, dann einen Tag später Kommando zurück (Pentaradio berichtete) neben CVE pflegt Mitre Corp. eine weniger bekannte Datenbank: CWE (Common Weakness Enumeration), ein Klassifizierungssystem für Arten von Sicherheitslücken wir besprechen die jährliche Rangliste der CWE Top 25 mit Stand von 2024 wertvoll, weil man so als interessierter Laie oder Programmierer-Generalist ein Gefühl für wichtige Angriffsvektoren bekommt Platz 1: CWE-79; fehlerhafte Neutralisierung von Eingaben während der Erzeugung von Webseiten ("Cross-Site Scripting", XSS) siehe Beispielbild im Link Webseiten können JavaScript-Code enthalten, der auf dem Browser des Endanwenders ausgeführt wird wenn Webseiten aus Eingaben anderer Benutzer zusammengebaut werden, können diese Code einschleusen Lösung: Escaping (Entfernen oder Ersetzen von Zeichen mit syntaktischer Bedeutung), kann durch Template Engines teilweise automatisiert werden passend dazu Platz 7: CWE-78; fehlerhafte Neutralisierung von Eingaben während der Erzeugung von Befehlszeilen außerdem Platz 13: CWE-77; dasselbe für alle anderen Befehlssprachen, die nicht JavaScript oder die System-Shell sind allgemeiner als Platz 12: CWE-20; unzureichende Überprüfung von Eingaben Lösung: "assume all input is malicious"; nur Eingaben akzeptieren, die strikten Formatvorgaben folgen (z.B. unter Einsatz von regulären Ausdrücken, siehe STP021) Platz 2, 6 und 20: CWE-787 und CWE-125; Schreiben bzw. Lesen außerhalb des allokierten Speicherbereichs ("Out-of-Bounds Write/Read") sowie als übergeordnete Kategorie CWE-119; allgemeiner Pufferüberlauf ("Buffer Overflow") und passend dazu Platz 8: CWE-416; Benutzung nach dem Freigeben ("Use after Free") alle bereits besprochen in STP047 Lösung: speichersichere Programmiersprachen, Speicherprofiling-Tools wie Valgrind (siehe STP076) Platz 3: CWE-89; SQL-Injektion SQL siehe STP012: Abfragesprache für relationale Datenbanksysteme Beispiel siehe XKCD 327 Lösung: Datenwerte von der Abfrage trennen (z.B. SELECT * FROM users WHERE name = 'Alice' -> SELECT * FROM users WHERE name = $1 mit Datensatz ["Alice"]) passend dazu Platz 11: CWE-94; Code-Injektion (dasselbe für Programmcode); Überlapp zu CWE-77 Platz 4: CWE-352; Cross-Site Request Forgery (CSRF) Angreifer möchte im Namen des Opfers eine Aktion ausführen (z.B. auf Rechnung des Opfers in einem Webshop bestellen) Angreifer schiebt dem Opfer ein manipuliertes HTML-Formular unter, dass beim Abschicken die gewünschte Aktion auslöst, aber mit den Cookies (und damit der Identität des Opfers) Lösung: CSRF-Tokens (echte HTML-Formulare erhalten ein einmalig nutzbares Token, dass nicht vom Angreifer gefälscht werden kann) passend dazu Platz 19: CWE-918; Server-Site Request Forgery (SSRF) dabei manipuliert der Angreifer nicht ein menschliches Opfer oder einen Webclient, sondern einen Webserver, mit seinem privilegierten Zugriff andere Webserver abzufragen Platz 5: CWE-22; Pfaddurchquerung ("Path Traversal") z.B. bei Webservern mit statischen Inhalten: entsprechende Dateien liegen im Dateisystem in einem bestimmten Ordner Dateien außerhalb dieses Ordners sollen eigentlich nicht zugreifbar sein, aber manchmal geht http://example.com/../../../etc/passwd oder dergleichen Lösung: magische Pfadelemente wie .. (bei Pfaden) oder / (bei Dateinamen) ablehnen Feedback zu STP063 Alex schreibt: danke für den Podcast. Ich bin wie immer weit im Rückstand mit Hören, habe zu Folge 63 aber mal die Turing-Maschine für die Subtraktion neu gebastelt. [...] Den Input muss man mit folgender 0 eingeben, also 1110110 z.B. Gebaut habe ich das auf https://turingmachinesimulator.com/. //---------------------------------------------------------------------- //Syntax: //-------CONFIGURATION name: sub init: q0 accept: qe //-------DELTA FUNCTION: //[current_state],[read_symbol] //[new_state],[write_symbol],[>|<|-] // < = left // > = right // - = hold // use underscore for blank cells q0,1 // 1en 1.Op überspringen q0,1,> q0,0 q1,0,> q1,0 // 0en überspringen q1,0,> q1,1 q2,1,> q2,0 // mehr als eine 1 im 2. Op? Ja->q5, nein->q3 q3,0,< q2,1 q5,1,> q5,1 // 1en 2.Op überspringen, dann auf letzte 1 des 2.Op q5,1,> q5,0 q6,0,< q6,1 // letzte 1 des 2. Op durch 0 ersetzen q7,0,< q7,1 // zurück, 1en 2. Op überspringen q7,1,< q7,0 q8,0,< q8,0 // zurück, 0en überspringen q8,0,< q8,1 // letzte 1 des 1. Op auf 0 setzen, zurück zu q1 q1,0,> q3,1 // letzte 1 des 2. Op auf 0 setzen q4,0,< q4,0 // zurück, 0en überspringen q4,0,< q4,1 // letzte 1 des 1.Op auf Null setzen, zum Ende qe,0,>

  • S1 · E77
    Aug 21, 2025 · 57 min

    STP077: Liste von Listen

    Als der inoffizielle Wikipedia-Vorlesepodcast sehen wir es als unsere Pflicht, eine Eigenheit dieser anzusprechen: nämlich Listen von Listen, obwohl es uns eigentlich um Listen im Speicher geht. Shownotes Rückbezüge: fundamentale Datenstrukturen siehe STP071: Felder/Listen, assoziative Datenfelder (Maps), Graphen Frage: Wie stellt man solche Datenstrukturen im Speicher dar? Gibt es darauf überhaupt die eine richtige Antwort? algorithmische Komplexität siehe STP029: Liste mit n Elementen ausdrucken in O(n), aber sortieren in O(n log(n)) bis O(n^2) Speicherallokation siehe STP047 und Speicherschutz siehe STP019: Bezug wird gleich klar werden Listen kann man als verkettete Liste darstellen klassisches Studienobjekt in Erstsemester-Datenstrukturen-Vorlesungen intuitiv verständlich: Parallele zu segmentierten Halsketten wahlweise einfach oder doppelt verkettet effiziente Operationen: Einfügen am Ende, Entfernen am Ende ineffiziente Operationen: Einfügen in der Mitte, Wahlzugriff/Suche Vergleichstabelle mit Darstellung der Zeiteffizienz alles in allem durchwachsene Performance -> geht es besser? alternative Strategie: interne Darstellung der Liste als balancierter Baum (oder evtl. "ausgeglichener Baum") außerdem Link auf die englische Wikipedia, die nicht nur unbalancierte, sondern auch balancierte Bäume zeigt kann nur sortierte Listen darstellen Idee: Wurzelknoten hat das Median-Element, dann der linke Ast alle kleineren und der rechte Ast alle größeren Elemente im Grunde alle gängigen Operationen mittelschnell: Wahlzugriff/Suche, Einfügen an beliebigen Stellen, Entfernen von beliebigen Stellen (Änderungen erfordern im Allgemeinen ein Austarieren des Baumes) große Variation von Implementationsstrategien für dieses Balancieren -> hier nicht verkettete Listen und balancierte Bäume sehen auf dem Papier ziemlich effizient aus, haben aber in ihrer reinen Form pathologisch schlechtes Speicherverhalten hoher Platzverbrauch: z.B. bei einfach bzw. doppelt verketteten Listen muss zu jedem Element müssen noch eine bzw. zwei Speicheradressen abgelegt werden hohe Allokationslast: wenn nicht eine Arena oder ein vergleichbarer Small Object Allocator verwendet wird schlechte Lokalität: beim Durchlaufen nachfolgender Elemente werden im schlimmsten Fall ständig unterschiedliche Speicherseiten getroffen, was fortlaufend Seitenfehler verursachen kann in der Praxis mit Abstand dominante Implementationsstrategie: dynamische Felder Beobachtung: Einfügen oder Löschen an beliebigen Stellen wird kaum gemacht; man hängt eher mehrmals ans Ende an und sortiert dann, falls nötig Idee: Optimieren auf Einfügen am Ende bei möglichst optimalen Speicherverhalten Umsetzung: einfaches Feld (ein fortlaufendes Stück Speicher, in dem mehrere Elemente hintereinander abgelegt werden) mit aktuellem Füllstand N und Kapazität K Einfügen ans Ende: normalerweise einfach N erhöhen; wenn N nicht in K passt, größeren Speicher reservieren, alles hinüberkopieren und die alten Speicherallokation verwerfen Löschen vom Ende: einfach N reduzieren, keine Deallokation erforderlich Einfügen am Anfang oder in die Mitte: alle Elemente dahinter nach hinten verschieben nahezu optimales Speicherverhalten von dynamischen Feldern begründet ihre Dominanz Platzverbrauch: neben der Speichergröße der Elemente selber nur zwei Zahlen (N und K) Allokationslast: Vergrößern geht für gewöhnlich in exponentiellen Schritten und wird damit für wachsende Listen immer seltener nötig Lokalität: lineare Suche durch die Liste geht linear durch den Speicher hindurch -> folgende Speicherseiten können vom Prozessor oft schon auf Verdacht vorgeladen werden trotzdem: die anderen Datenstrukturen haben auch ihre Berechtigung (z.B. modifizierte balancierte Bäume als Basis für Datenbank-Indizes) Xyrill will auch noch auf analoge Weise über Maps und Graphen reden -> weiter in STP079

  • S1 · E76
    Jul 31, 2025 · 58 min

    STP076: Debugging

    Die Zeiten, in denen wie von Grace Hopper "actual bugs" in Computern gefunden werden, sind wohl weitestgehend vorbei. Trotzdem ist Debugging bis heute eine Sache, um die man in der IT nicht herumkommt. Shownotes Wikipedia definiert den Begriff: Als Debuggen (dt. Entwanzen) oder Fehlerbehebung bezeichnet man in der Informatik den Vorgang, in einem Computerprogramm Fehler oder unerwartetes Verhalten zu diagnostizieren und zu beheben. Die Suche von Programmfehlern (sogenannten Bugs) ist eine der wichtigsten und anspruchsvollsten Aufgaben der Softwareentwicklung und nimmt einen großen Teil der Entwicklungszeit in Anspruch. Ein guter Programmierer muss daher auch das Debuggen beherrschen und umgekehrt: Nicht jeder gute Programmierer ist auch ein guter Debugger. Xyrill hat eine Anekdote: Firefox im Hotel-WLAN hängt beim Starten vier Minuten nicht dramatisch, könnte man auch hinnehmen (oder halt auf einen anderen Browser wechseln) Xyrill war aber in der Stimmung, zu debuggen Kategorie 1: Werkzeuge zum Mitlauschen traceroute (bzw. tracert unter Windows): Nachverfolgung der Netzwerkroute zu einem bestimmten Ziel anhand von Ping-Paketen mit begrenzter TTL; stark variable Pings oder plötzliche Anstiege des Pings deuten auf ein Problem an dem entsprechenden Hop hin tcpdump und Wireshark: Mitschneiden aller Netzwerkpakete, die über ein Netzwerk-Interface versendet oder empfangen werden (evtl. mit Suchmuster, z.B. "nur auf Port 80" oder "nur für Ziel-/Quelladresse 192.168.0.1") mitmproxy et al: Fangnetz für HTTP-Anfragen und -Antworten, die von einem Prozess geschickt und empfangen werden (quasi wie tcpdump, aber einige Netzwerkschichten höher); super zum Reverse-Engineering von webbasierten APIs mal nicht Netzwerk: strace listet alle Syscalls (Systemrufe) auf, die ein Prozess während seiner Lebenszeit macht (siehe Beispiel unten) zurück zum Hotel-WLAN-Beispiel: strace zeigt Timeout bei DNS-Anfrage zum eigenen Hostnamen jeweils 2x nach 120s Grund für diese Anfragen bleibt unklar, aber die Lösung ist eindeutig: expliziter Eintrag für den eigenen Hostnamen in /etc/hosts, um die DNS-Abfrage zu umgehen Kategorie 2: Werkzeuge zum Nachverfolgen printf-Debugging: im Programmcode vorrübergehend Befehle einbauen, die zu sinnfälligen Zeitpunkten Logmeldungen ausdrucken, insb. beinhaltend den aktuellen Zustand von bestimmten Variablen (sprich: transiente Form von Logging, siehe STP032) Debugger wie gdb: Ausführung eines Programms bis zum Moment des Crashs oder bis zu benutzerdefinierten Haltepunkten; dann schrittweise Ausführung bzw. Inspektion von Variablen (flexibler als printf-Debugging, aber erfordert direkten Zugriff auf den Prozess) Profiler wie valgrind: Ausführung eines Programms und währenddessen Erfassung von Statistiken zu Laufzeit- und Speichernutzung, um Speicherzugriffsfehler oder Ineffizienzen aufzudecken Kategorie 3: Werkzeuge zum Zurückverfolgen Bisektion z.B. mit git bisect: Aufspüren derjenigen Änderung in einem Versionsverwaltungssystem, die eine bestimmte Verhaltensänderung (z.B. einen Bug oder einen Performance-Einbruch) ausgelöst hat Beispiel einer strace-Ausgabe für den Befehl mv /tmp/foo /tmp/bar (stark verkürzt): $ strace mv /tmp/foo /tmp/bar execve("/usr/bin/mv", ["mv", "/tmp/foo", "/tmp/bar"], 0x7fff820357b0 /* 67 vars */) = 0 ... (ca. 60 Zeilen an Setup-Phase der libc und anderer Shared Libraries ausgelassen) ... ioctl(0, TCGETS, {c_iflag=ICRNL|IXON|IUTF8, c_oflag=NL0|CR0|TAB0|BS0|VT0|FF0|OPOST|ONLCR, c_cflag=B38400|CS8|CREAD, c_lflag=ISIG|ICANON|ECHO|ECHOE|ECHOK|IEXTEN|ECHOCTL|ECHOKE, ...}) = 0 renameat2(AT_FDCWD, "/tmp/foo", AT_FDCWD, "/tmp/bar", RENAME_NOREPLACE) = -1 EEXIST (File exists) openat(AT_FDCWD, "/tmp/bar", O_RDONLY|O_PATH|O_DIRECTORY) = -1 ENOTDIR (Not a directory) newfstatat(AT_FDCWD, "/tmp/foo", {st_mode=S_IFREG|0644, st_size=0, ...}, AT_SYMLINK_NOFOLLOW) = 0 newfstatat(AT_FDCWD, "/tmp/bar", {st_mode=S_IFREG|0644, st_size=0, ...}, AT_SYMLINK_NOFOLLOW) = 0 geteuid() = 1001 faccessat2(AT_FDCWD, "/tmp/bar", W_OK, AT_EACCESS) = 0 renameat2(AT_FDCWD, "/tmp/foo", AT_FDCWD, "/tmp/bar", 0) = 0 lseek(0, 0, SEEK_CUR) = -1 ESPIPE (Illegal seek) close(0) = 0 close(1) = 0 close(2) = 0 exit_group(0) = ? +++ exited with 0 +++

  • S1 · E75
    Jul 10, 2025 · 56 min

    STP075: Prozessorarchitekturen im Vergleich

    Nach einer sehr deutlichen Einordnung der Aufnahmezeit kommen wir im Wesentlichen zu den Unterschieden zwischen x86 und ARM. Natürlich wird auch geklärt, was das ist. Gegen Ende gibt es noch ein paar Meinungen und Weissagungen zum Thema KI. Shownotes Rückbezug STP011: grundsätzliche Beschreibung von Maschinensprache siehe Beispiel unter dem obenstehenden Link Maschinensprache ist spezifisch für die Prozessorarchitektur, genauer die Befehlssatzarchitektur (instruction set architecture, ISA) heutzutage relevante ISA x86: PCs, Notebooks, Server, Supercomputer, Apple Macs bis 2020 ARM: Smartphones, Tablets, Apple Macs seit 2020, Einplatinencomputer (SBC) wie Raspberry Pi Embedded: AVR, MIPS, etc. Hochleistungsrechnen: neben x86 noch Power und SPARC Neuentwicklungen: RISC-V, LoongArch Warum ist die Wahl der ISA wichtig? ISA beschreibt nominal, wie ein CPU die Bits in einer ausführbaren Binärdatei (sprich: die kodierte Form der Maschinensprache) zu interpretieren hat daraus als Konsequenz Festlegung von Hardware-Parametern wie der Adressbreite oder der Anzahl und Größe der verfügbaren Register Designentscheidungen in der ISA wirken sich auf die maximal erreichbare Performance und auf die Energieeffizienz aus klassischerweise Gegenüberstellung zweier verschiedener Design-Philosophien: Complex Instruction Set Computing (CISC) und Reduced Instruction Set Computing (RISC) (die Grenzen verschwimmen aber in der Praxis) historischerweise war CISC die Domäne großer CPU-Hersteller, die sich ein kompliziertes Design leisten konnten, um dem Programmierer Arbeit abzunehmen (z.B. Intel); und RISC die Domäne kleiner CPU-Hersteller, die aus möglichst wenig Arbeitseinsatz möglichst viel erreichen wollten Was steht in einem Maschinencode-Befehl drin? grundsätzlich eine Operation, die ausgeführt wird (z.B. "Addition zweier 64-Bit-Zahlen") als Quellen für Argumente und Ziel für das Ergebnis: entweder Register, Speicher oder Immediate-Argumente Beispiel CISC: 20 verschiedene Ausführungen des ADD-Befehls in x86-64 Beispiel RISC: 2 verschiedene Ausführungen des ADD- bzw. ADDI-Befehls in RISC-V (RV32I) wenn RISC wie bei RISC-V eine Load/Store-Architektur verwendet, muss man also im Zweifelsfall Argumente erst aus dem Speicher in Register laden dadurch tendenziell mehr Maschinencode, aber weniger Komplexität in der CPU Abwägungen zwischen Energieeffizienz (ARM) und Performance (x86) aktueller ARM-Befehlssatz (A64) hat durchgängig 4 Byte große Befehle, was das Dekodieren vereinfacht; x86-Befehle haben eine variable Breite zwischen 1 und 15 Byte x86 hat eine lange Pipeline, um u.a. die komplexen Befehle in kleinere Teilschritte (Micro-Operations) zu zerlegen oder bestimmte häufige Befehlssequenzen in effizientere Gruppen (Macro-Operations) zu fusionieren und damit die Performance zu steigern; ARM-Prozessoren machen das nicht und sparen dadurch Energieaufwand x86 hat für bestimmte Rollen designierte Spezialregister, die je nach Befehl feste Bedeutungen haben; ARM (und RISC allgemein) verwendet für fast alles 31 General-Purpose-Register

Showing 1–20 of 20 episodes