Magic bytes (sygnatura pliku) to charakterystyczne bajty na początku pliku, po których można rozpoznać jego rzeczywisty format niezależnie od rozszerzenia. Na przykład plik PNG zaczyna się od bajtów 89 50 4E 47.
Dlaczego rozszerzenie nie wystarczy?
Rozszerzenie i nagłówek Content-Type przesłane przez użytkownika można dowolnie zmienić. Napastnik może wysłać skrypt PHP nazwany foto.jpg. Dlatego serwer powinien sprawdzać zawartość pliku, np. przez finfo_file() w PHP.
Bezpieczne przesyłanie plików
- zezwalaj tylko na listę dozwolonych typów,
- zmieniaj nazwę pliku i zapisuj go poza katalogiem wykonywalnym,
- ograniczaj rozmiar,
- skanuj pliki, jeśli to możliwe.
Jak sprawdzić typ pliku w PHP?
Funkcja finfo_file() z rozszerzenia Fileinfo odczytuje typ MIME z zawartości pliku, a getimagesize() weryfikuje, czy obraz faktycznie ma poprawne wymiary. Wynik porównaj z listą dozwolonych typów i zapisuj plik pod losową nazwą. Dla obrazów dobrym zabezpieczeniem jest ponowne zakodowanie pliku przez bibliotekę graficzną, które usuwa osadzone fragmenty kodu.
Czy sprawdzenie magic bytes wystarczy?
Nie. Plik może mieć poprawną sygnaturę i złośliwą treść na dalszych bajtach. To jedna z warstw ochrony obok list dozwolonych typów i izolacji uploadów.
Podobnie jak przy zabezpieczaniu aplikacji przed SQL Injection, podstawą ochrony jest traktowanie wszystkich danych od użytkownika jako niezaufanych.
Zobacz w praktyce
Jak zabezpieczyć aplikację przed SQL Injection
Konfiguracja CDN – cache, czyszczenie i reguły
Ochrona przed atakami brute force – jak zabezpieczam logowanie na stronie i serwerze