Verborgen bestanden weer zichtbaar maken
Kopieerbeveiligingssoftware wil bestanden leesbaar houden, maar beschermen tegen kopiëren. We hebben een dergelijke beveiliging voor usb-sticks geanalyseerd en laten zien wat je daarbij leert over bestandssystemen en hoe Windows intern werkt. Sylvester Tr
We kregen een tijd geleden een usb-stick in handen die beveiligd was tegen kopiëren. De bestanden die erop stonden waren wel te lezen en af te spelen (want het waren audiobestanden), maar de bedoeling erachter was dat je ze niet kon kopiëren. In principe is dat nauwelijks te voorkomen, zeker niet als de gebruikte hardware en het medium geheel door de gebruiker gecontroleerd worden – zoals bij pc’s en usb-sticks het geval is. Als iets leesbaar is, dan kun je de gelezen data ook ergens heen schrijven en op die manier kopiëren. Onze interesse was gewekt, en dus begonnen we een speurtocht naar de manier waarop ontwikkelaars van software het kopiëren van bestanden door gebruikers willen tegengaan.
Daar gebruikten we alleen de standaardmiddelen van Windows voor. Je hebt er geen gespecialiseerde software voor nodig omdat de bestanden inderdaad alleen verborgen worden. Een werkzame kopieerbeveiliging kun je van dergelijke pure software-oplossingen dan ook niet verwachten.
Net als de kopieerbeveiligingsmechanismen voor audio-cd’s proberen ze te breken met conventies en impliciete aannames. Bij audio-cd’s worden met opzet ‘foutieve’ cd’s geproduceerd en op usb-sticks worden ‘illegale’ bestandsnamen gebruikt om de gangbare applicaties in de war te brengen.
Ook al deugen dergelijke tools niet voor ‘beveiliging’, je kunt toch veel plezier beleven aan het analyseren ervan. Daarbij leer je ook een hoop over Windows en bestandssystemen.
OP JACHT
De usb-stick werd beveiligd door de tool USB Copy Protection van Kakasoft. Voor onze experimenten hebben we de trialversie van de software gebruikt, die alle functies heeft, maar beperkt is tot 5 dagen. Daar hebben we bestanden mee op een nieuwe usb-stick gezet.
Als je een op een dergelijke manier geprepareerde usb-stick opent met Windows Verkenner, dan is daar niets op te zien behalve een uitvoerbaar bestand met de naam Client.exe. Na het starten daarvan krijg je een op Verkenner lijkende interface te zien waarmee je toegang tot de beveiligde bestanden kunt krijgen.
Voor een paar bestandsformaten heeft die ‘client’ ook een viewer, en andere bestanden worden geopend met de op het systeem geïnstalleerde programma’s. Met de interface zijn maar beperkte bestandsmanipulaties mogelijk, die bepaald worden door hoe je de beveiliging hebt ingesteld.
MET EEN BREEKIJZER
Als je de beveiligde bestanden wilt kopiëren, moet je die client dan ook op de een of andere manier omzeilen. Dat kan bijvoorbeeld met grof geschut: maak een compleet image van de usb-stick en zet die op een andere stick. Je hebt de bestanden dan wel gekopieerd, maar je krijgt ze niet zo snel uit de omgeving van de client. Je hebt dan simpel gezegd twee ‘beveiligde’ usb-sticks.
Wellicht kan het ook wat eleganter en doelgerichter dan het bestandssysteem, de beveiliging en de beveiligde bestanden in zijn geheel dupliceren? De beveiligde bestanden moeten immers ergens opgeslagen staan.
In theorie kunnen ze bij de client ingecompileerd zijn. Maar dan moet de software die zelf vroeger of later ook extraheren, zodat normale programma’s ze in elk geval kunnen openen en weergeven. Als je naar de grootte van het client-programma kijkt, kun je zien dat de bestanden daar niet inzitten. Dus moeten die ergens anders op de schijnbaar lege usb-stick staan.
STANDAARDMIDDELEN
Bij Verkenner hoeft wat je te zien krijgt niet per se wat met de waarheid te maken hebben – zie het volgende artikel. Als je bij de opties van Verkenner aangeeft dat je ook verborgen bestanden en systeembestanden wilt zien, duiken op de usb-stick onder meer de mappen ProgramData en HPSafeBox op.
Die eerste bevat programmabestanden en bibliotheken voor de client en is verder niet interessant. De map HPSafeBox is wat dat betreft veelbelovender. Die lijkt eruit te zien als een map met printers. Als je de map opent, staan daar inderdaad de lokaal geïnstalleerde printers in. Dat komt doordat in HPSafeBox een desktop.ini-bestand staat met de volgende inhoud:
[.ShellClassInfo]CLSID={2227a280-3aea-1069a2de-08002b30309d}
Die Class-ID (CLSID) meldt Verkenner dat de lokale printers getoond moeten worden in plaats van de werkelijke mapinhoud. Hoe dat precies werkt leggen we in het volgende artikel uit. Met Verkenner kom je hier dus niet verder.
De volgende stap is dan ook het gebruiken van PowerShell. Met dir -force D:\ krijg je de ware inhoud van de usb-stick te zien. De parameter -force is nodig om verborgen bestanden, systeembestanden en dergelijke te laten weergeven. Met het commando dir -force D:\HPSafeBox\ krijg je drie items te zien, die zich daadwerkelijk in die map bevinden: een map met de naam ‘Important Folder’ en de bestanden ‘con.{d3e34b21-9d75-101a-8c3d-00aa001a1652}’ plus de bovengenoemde desktop.ini.
Wat het doel van het bestand con.{...} is, hebben we niet kunnen achterhalen. Het bestand gebruikt blijkbaar een Class-ID als bestandsnaamextensie. Daardoor wordt een Paint-afbeelding als pictogram
van het bestand weergegeven, wat gebruikers vermoedelijk in verwarring zal brengen. De inhoud van het bestand bestaat uit 1023 null-bytes, wat natuurlijk geen toeval is, maar wat het nut daarvan is konden we niet herkennen. Dan maar verder met de map ‘Important Folder’. Ga daar naartoe met het commando cd ‘D:\HPSafeBox\Important Folder’. Als het pad een spatie bevat, moet je daar aanhalingstekens omheen zetten. Na het intypen van het commando dir zie je dat er in die ‘belangrijke map’ alleen een submap staat met de naam ‘Com1.{d3e34b21-9d75-101a8c3d-00aa001a1652}’.
Er staat je dan een onaangename verrassing te wachten als je met het commando cd naar die map probeert te gaan: de shell geeft de mededeling ‘Cannot find path […] because it does not exist.’. Het lijkt daarmee alsof die map in zijn geheel niet lijkt te bestaan.
Dat ligt dan niet aan de Class-ID in de mapnaam, maar aan het deel ervoor. ‘Com1’ is sinds DOS 1.0 namelijk geen legale naam voor bestanden en mappen, maar staat voor de eerste seriële poort van een computer (zie de link op de laatste pagina van dit artikel). Of een computer überhaupt nog een seriële interface heeft, speelt daarbij net zo min een rol als de bestandsnaamextensie.
Ook PowerShell en het onderliggende .NET-framework volgen die oeroude regels en komen bij dergelijke namen daardoor in de problemen. Hoe PowerShell daarmee omgaat, hangt van je versie en van het .NET-framework af – de volgende werkwijze werkt met Windows PowerShell 5.1.
GEDOE
PowerShell 5.1 doet wel moeilijk als je met cd naar de map navigeert, maar kan in elk geval wel de inhoud van de map weergeven. Die moet je dan wel
tussen aanhalingstekens zetten en afsluiten met een backslash: dir ‘Com1.{d3e34b21-9d75-101a8c3d-00aa001a1652}\’. Omdat de naam ook het automatisch aanvullen tegenhoudt, helpt het daarbij overigens om de oude 8.3-namen te gebruiken (zie het kader links). Dat bespaart je aardig wat typwerk: dir ‘Com1~1.{d3\’.
De inhoud van de map ziet er op het eerste oog echter niet veelbelovend uit: ⍰⍰⍰.. Er staat slechts een enkele map in, waarvan PowerShell de naam echter alleen in vraagtekens toont met uitzondering van de twee punten aan het eind. Om te kunnen achterhalen hoe de naam opgebouwd is, kun je het volgende commando uitvoeren:
(dir ‘Com1~1.{d3\’).Name | Format-Hex -Encoding BigEndianUnicode
Met dir ‘Com1~1.{d3\’ krijg je de inhoud van de map. Het commando staat tussen haakjes, zodat van het resultaat ervan de eigenschap .Name geselecteerd kan worden. Om ervoor te zorgen dat je niet weer alleen vraagtekens te zien krijgt, wordt die naam door Format-Hex -Encoding BigEndianUnicode vervolgens als hexa-decimaal geformateerde bytevolgorde weergegeven.
De Encoding- parameter is nodig omdat de uitvoer ander de ASCII-tekenset gebruikt en niet alle gebruikte tekens in de ASCII-ruimte weer te geven zijn. Het gebruikte BigEndianUnicode betekent UTF-16. Andere waarden zoals Unicode en UTF8 zouden ook mogelijk zijn, maar die zijn niet zo goed leesbaar:
00 7F 00 7F E3 47 00 2E 00 2E
De 16-bit groepen 00 7F en 00 2E staan daarbij voor hun ASCII-tegenhanger. De naam begint dus met twee niet weer te geven ASCII-stuurtekens (‘Delete’, U+007F) en eindigt met een dubbele punt, zoals die aan het eind van de bestandsnaam staat (U+002E). Daartussen staat het Unicode-teken U+E347.
De beide Delete-stuurtekens verhinderen dat je de naam eenvoudig naar de shell kopieert en invoegt, omdat die bij het invoegen geïnterpreteerd worden. Die tekens zijn ook in de 8.3-naam van de map terecht gekomen, zodat daar geen eenvoudige oplossing voor is. U+E347 stamt uit de private-use-zone van de Unicode-tekenset – en heeft dus expliciet geen gestandaardiseerde betekenis. Het heeft hier als nut dat het door zo min mogelijk lettertypen weergegeven kan worden en moet applicaties die daar niet mee overweg kunnen van de wijs brengen.
De betekenis van de dubbele punt aan het eind werd voor ons niet duidelijk. Wellicht leidt dat tot problemen bij programma’s die ‘begrijpelijke’ bestandsextensies verwachten. Of het moet programma’s ertoe overhalen het koeterwaals voorafgaande aan die punten te negeren en daardoor bij de naam ‘..’ uit te komen, wat voor de bovenliggende map staat.
In ieder geval is het als je de precieze aard van de namen weet mogelijk om daar een pad van te maken en er met dir achter te komen wat er zich in de onuitspreekbare map bevindt. PowerShells vanaf versie 6 hebben helaas geen syntaxis om Unicode-tekens om te zetten naar strings met escapes. Vanaf versie 6 gaat