Secure by Design - Hoofdstuk 1

Ingediend door Dirk Hornstra op 19-jan-2020 22:00

Van november 2018 tot en met september 2019 hebben we met de "back-enders" van TRES het boek "Clean Code" doorgenomen. Hierbij het linkje naar het laatste hoofdstuk, hoofdstuk 17: link. Op deze pagina staan ook de linkjes naar de voorgaande hoofdstukken. De vraag was wat het volgende boek zou worden, de keuze is gevallen op het boek "Secure by Design", geschreven door de 3 D's: Dan Bergh Johnsson, Daniel Deogun en Daniel Sawano. Dan is het mooi dat de volgende D (Dirk) er een samenvatting van maakt :) Denk je bij "secury by design" al gauw dat het over cross-site-request-forgery, sql-injection en headers zou gaan (toch al gauw de bevindingen als sites getest worden), de focus ligt (in ieder geval in het begin) ook hier weer op "clean code".

Voorwoord

Daniel Terhorst (nog een D, ingehuurd?) heeft het voorwoord geschreven. Hij beschrijft hoe hij met een scriptje kon monitoren wie als eerstvolgende collega ontslagen zou worden (account werd van tevoren gelockt), hoe mensen documenten "beveiligd met een wachtwoord" doorstuurden en die hij met een gevonden password-cracker un-encrypted weer terug stuurde. Doordat hij kritisch was en zo veiligheidszaken benoemde is hij doorgegroeid naar de rol van "InfoSec Officer". Bij een test koppelde een tester terug dat een veld niet de maximale 30 tekens-controle bevatte. Door er 35.000 tekens in te gooien liet je de hele applicatie vastlopen: een heftige DDOS. Ondanks alle password-managers, haveibeenpwnd-controle, je wordt altijd op het zwakste punt afgerekend. Met dit boek willen de auteurs demonstreren dat beveiliging vooral een ontwerp-overweging is. Bij het bouwen moet je dit al meenemen, niet op een later tijdstip nog wat zaken erom heen bouwen om de boel "veilig te maken". Daniel benoemt ook het andere issue, slechte error-afhandeling. Je hebt 2 code-stromen: alles gaat goed en het pad waarbij het niet goed gaat. In dat geval heb je vaak een stuk spaghetti-code met try-catches en halfslachtige manieren om errors af te handelen. Volgens Joe Armstrong, maker van de Erlang programmeertaal is de enige juiste methode om een error af te handelen om "het te laten crashen". Bij die programmeertaal mag dat misschien wel zo zijn, als je de standaard error laat zien heb je soms dat er juist bepaalde extra informatie op het scherm komt die je 1. de "normale" bezoeker niet wilt tonen (die wil je een nette melding laten zien) en 2. die soms teveel informatie teruggeeft (ASP.NET versie, pad van de bestanden...) wat je niet aan de scriptkiddies op je site wilt tonen. Kleinere onderdelen zijn beter te testen, minder plaatsen voor bugs om zich te verbergen. Maar als je systeem uit allemaal kleine onderdelen bestaat (microservices bijvoorbeeld) kan het één weer invloed op de ander hebben. We gaan nu dus volgens Domain Driven Design denken en de consequenties overdenken welke invloed het op de beveiliging kan hebben.

Voorwoord 2 / Bedankjes / Over het boek

Voordat we beginnen nog een kleine tekst over hoe de 3 schrijvers ertoe gekomen zijn om dit boek te schrijven. Er wordt verwezen naar Eric Evans die een boek over Domain-Driven-Design geschreven heeft. Echtgenotes en nog wat andere mensen worden bedankt. Het boek is primair geschreven voor software developers, maar andere mensen mogen/kunnen het boek natuurlijk ook lezen! Voor de code-voorbeelden is Java gekozen omdat dit voor de meeste developers (C / C#) ervaring goed te lezen is.

Hoofdstuk 1 - waarom het ontwerp invloed heeft op de veiligheid

We beginnen met een voorbeeld van hoe het niet moet. Er wordt met een project gestart. "Security" wordt op het backlog gezet, collega's dragen wat security-libraries aan, dus alles lijkt geregeld. Hoewel je tijdens het ontwikkelen al continu zou moeten denken over wat jouw beslissing/aanpak voor impact heeft op veiligheid doe je dat niet. Je bent andere dingen aan het uitzoeken, loopt tegen problemen aan of zit juist goed in de flow. De security-taken op het backlog krijgen een steeds lagere prioriteit en uiteindelijk is het zover, de code is klaar voor productie. Wat ga je doen? Security-audit en penetratie-test. Met tig bevindingen waardoor je extra weken nodig hebt om de boel te fixen. Of die stappen dan maar overslaan, code live zetten en na een half jaar in de media verschijnen omdat er niet publieke data gelekt is...

Vragen die bij de auteurs opkomen zijn:

- waarom krijgen security-taken altijd een lagere prioriteit dan andere taken?

- waarom zijn ontwikkelaars over het algemeen niet geïnteresseerd in security-gerelateerde zaken?

- iedereen zegt dat ontwikkelaars steeds meer op security gericht moeten zijn, waarom doet nog niet iedereen dat dan?

- waarom realiseren managers niet dat er net zoals je testers in het team hebt ook security-experts in je team moet hebben?

De auteurs geven aan dat niet zo zeer "security" continu in je gedachten moet zitten, maar je naar het "design" moet kijken. Aan de hand van voorbeelden wordt dat in dit hoofdstuk behandeld.

1.1 Security is iets wat je aandacht vraagt, het mag nooit een "feature" zijn

Het voorbeeld van de eerste bankoverval wordt gegeven op de Öst-Gotha Bank in 1854 in Zweden. De buitendeur is afgesloten, maar buiten hangt ergens de sleutel aan een haakje. De binnendeur heeft dikke sloten, maar de scharnieren zijn van inferieure kwaliteit: eitje voor de inbrekers. De features waren: we zetten sloten op de buitendeur en we zetten dikke sloten op de binnendeur. De formulering had moeten zijn "hoe zorgen we dat mensen niet met geld naar buiten kunnen lopen". Dan waren ook de andere onderdelen meegenomen in de beoordeling.

1.1.2 Security aandachtspunten en features

Software wordt vaak beschreven als features. Ik wil op de site via een inlogscherm bij mijn foto's kunnen komen. Maar als de foto-pagina publiekelijk toegankelijk is, dus als iemand de URL weet en erbij kan komen, is dat inlogscherm niet van belang. De stelling had hier moeten luiden dat je "bij je foto's wilt kunnen komen nadat je geauthenticeerd bent en gecontroleerd kan worden of je bij de foto's mag komen".

1.1.3 Categorieën van security aandachtspunten CIA-T

- Confidential (vertrouwelijk) - bepaalde informatie van jou die niet voor andere mensen bedoeld is.

- Integrity (integriteit, betrouwbaarheid) - het is belangrijk dat informatie niet verandert of alleen verandert bij speciale, geautoriseerde situaties.

- Availability (beschikbaarheid) - je gegevens zijn binnen afzienbare tijd beschikbaar. Als de brandweer naar een brand wordt gestuurd moeten ze de locatie weten, als dat pas na 2 uur wordt aangeleverd is het te laat.

Hierna volgen een aantal voorbeelden waarbij getoond wordt dat alle 3 onderdeel van je probleem kunnen uitmaken, maar dat ze qua impact kunnen verschillen.

Als jouw medische gegevens op straat liggen is confidential geschaadt: je bent boos. Als er fouten in staan (integrity, je linker-oog moet gelaserd worden, maar in het dossier staat het rechter-oog genoemd) is het verwarrend en ook gevaarlijk. En als tijdens de operatie je dossier helemaal niet beschikbaar is kan het dodelijk zijn (availability).

Als het over je bankrekening gaat, als je moet betalen en je kunt niet bij je internetbankieren (availability), dan is dat vervelend. Als je saldo door iedereen te raadplegen is (confidential) kan de bank een boze klant aan de balie/telefoon verwachten. Maar als je rekening waar je spaargeld op stond zonder af- of bijboekingen ineens 0 euro is geworden, dan is dat een catastrofe.

Na verloop van tijd is bij deze 3 C's de T toegevoegd van Tracability, wat staat voor het na de tijd kunnen controleren wie je data geraadpleegd heeft en wie jouw data bijgewerkt heeft. Na wat incidenten bij financiële sector en gezondheidszorg (Barbie lag in het ziekenhuis, verplegend personeel ging haar dossier even bekijken). Dit type logging is ook belangrijk voor de GDPR (General Data Protection Regulation) die in 2018 in de Europese Unie actief is geworden.

1.2 Het ontwerp definiëren

We kunnen allemaal onze code kloppen, slimme algoritmes bedenken. Je begint code in nuget-packages te plaatsen, zorgt met Dependency Injection en interfaces voor een stabiele structuur. En je overtreedt niet het Liskov Substitution Principle. Design / ontwerpen is het volledige plaatje. Design omvat het bouwen van je systeem en toepasbaar op alle gebieden, van code tot de architectuur. Het omvat ook de activiteiten die betrekking hebben op actief besluiten nemen.

1.3. De traditionele aanpak en de tekortkomingen

In de traditionele aanpak zou iedere ontwikkelaar een security-expert moeten zijn. Vink je lijstje met OWASP-controles en standaard web.config-items af en je bent klaar.

Maar door het afvinken van lijstjes kom je er niet. De auteurs tonen het voorbeeld van een inlog-procedure. Je komt hier binnen met een gebruikersnaam en wachtwoord. Beide velden zijn "gewone strings", dus je zou kunnen registeren met XSS zaken in je gebruikersnaam. In het volgende voorbeeld is de code aangepast en controleert een externe library de gebruikersnaam en ook worden waardes gecontroleerd of ze geen NULL waarde hebben.

Probleem hiervan is:

- je bent aan het bouwen. Je bent met business-logica bezig. Je moet nu je aandacht verdelen tussen deze zaken, daar gaat één van de twee minder aandacht krijgen.

- iedere developer moet een security-expert zijn. Elke dag komen er weer nieuwe risico's bij, hoe gaan we dit doen?

- de aanname wordt gedaan dat je even kunt bedenken welke kwetsbaarheden er mogelijk zijn. Zie ook het vorige punt, er komen later zero-day zaken bij.

1.4 / 1.4.1 Ontwerp zaken zo dat het secure is

Zorg dat de software die je schrijft aan de hoogst mogelijke standaard voldoet. Als voorbeeld krijgen we weer de inlognaam. Je weet dat de gebruikersnaam uit geselecteerde karakters mag bestaan (geen kleiner of groter dan teken), dus zet er een regex met validatie op. Hetzelfde geldt voor de lengte. Strings, int, bool, deze zijn volgens het boek primitieve types. In het voorbeeld wordt een eigen UserName-class aangemaakt waarin je al de restricties plaatst. Zo weet je ook zeker dat op andere plaatsen in je code hetzelfde type object met dezelfde restricties gebruikt wordt.

1.4.2 / 1.4.3 Voordeel van deze aanpak

- het onwerpen/bouwen van software, daar ligt de interesse en competentie van software developers, waardoor secure by design makkelijk uitvoerbaar is

- door te focussen op een goed design worden zowel business als security zaken met evenveel prioriteit opgepakt

- je hoeft geen expert te zijn om veilige code te bouwen

- door op het domein te focussen worden veel veiligheidszaken al impliciet opgelost

Maar blijf wel kritisch, want je lost er niet alle zaken op.

1.5 Strings

Controles op string-waardes:

- klopt de lengte?

- worden de juiste karakters en encoding gebruikt?

- is het input-format (postcode: 4 cijfers, spatie, 2 hoofdletters) juist?

1.5.1 / volgende - XML en "billion laughs"

We krijgen het voorbeeld van een stuk XML, met een Document Type Definition kun je de structuur aangeven. Daardoor kun je ook de tekst binnen nodes laten vervangen. In het voorbeeld zien we een stuk rampzalige code. Je hebt een lol node. Die lol-node bevat de tekst lol9. Die lol9 wordt vervangen met 10 lol8 tekst-items. Een lol8 tekst-item wordt vervangen door 10 lol7 tekst-items. Hierdoor groeit de tekst exponentieel.

Hoe fix je dit? We gaan eerst de parser onderzoeken.

Elke parser gedraagt zich anders, dus eerst OWASP raadplegen. Daar blijkt dat je wel zaken kunt uitschakelen, maar dat gaat dan weer ten koste van de usability. Hoe moet je hiernaar kijken? Is het een "bug" van de parser? Nee, het is gewoon "ongeldige data", dus je moet validatie op de input toepassen. In het boek wordt met een SAX parser (Simple API for XML) de validatie uitgevoerd.

Een andere aanpak is dat de code op zich niet verkeerd is. Maar door de opbouw raakt het geheugen "vol". Je zou dus ook limieten qua geheugen en/of quota's in kunnen stellen. Dit hoeft niet altijd afdoende te zijn, want als de verwerking parallel verloopt kan het zijn dat de limiet per proces niet geraakt wordt. Dus de combinatie met de SAX parser maakt het dan robuuster.

Deze combinatie is de aanpak waar de auteurs voorstander van zijn. Je plaatst een hek om het huis, maar omdat niet alles tegengehouden moet worden, zet je bepaalde zaken open. Je haalt niet het hele hek weg. Door de limiet op het geheugengebruik te zetten plaats je nog een waakhond in het huis. Wordt het hek platgewalst, dan hebben we nog een second line of defence. Wat we nu dus ook zagen bij het MCL, er is geconstateerd dat hackers een security-hole van Citrix gebruikt hebben, maar de volgende verdedigingslinie heeft deze actie gedetecteerd en de beheerders gealarmeerd.