Niedawno dowiedziałem się, że (przynajmniej w Fedorze i Red Hat Enterprise Linux) programy wykonywalne skompilowane jako pliki niezależne od pozycji (PIE) otrzymują silniejszą ochronę przed losową przestrzenią adresową (ASLR).
A zatem: Jak sprawdzić, czy określony plik wykonywalny został skompilowany w Linuksie jako plik wykonywalny niezależny od pozycji?
-pie -fpie
specjalne flagi kompilatora, aby skompilować program jako SROKA. Ten link zawierał jednak inne interesujące informacje - dziękuję!Odpowiedzi:
Możesz użyć
perl
skryptu zawartego whardening-check
pakiecie, dostępnego w Fedorze i Debianie (ashardening-includes
). Przeczytaj tę stronę wiki Debiana, aby uzyskać szczegółowe informacje na temat sprawdzanych flag kompilacji. Jest specyficzny dla Debiana, ale teoria dotyczy również Red Hata.Przykład:
źródło
sudo apt-get install hardening-includes
a następniehardening-check
skrypt wykonywalny perla jest dostępny na zwykłejPATH
(/usr/bin/hardening-check
); tylko nit: Zaproponuj usunięcie./
odpowiedzi ;-)devscripts
.Kiedyś
readelf --relocs
, aby sprawdzić, czy statyczne lub dynamiczne biblioteki PIC na x86-64 następujący sposób:Widzimy tutaj
R_X86_64_32
iR_X86_64_32S
. Oznacza to, że kod nie jest niezależny od pozycji. Kiedy odbudowuję bibliotekę z opcją -fPIC, otrzymuję:Ta metoda prawdopodobnie działa w przypadku plików wykonywalnych, ale nie użyłem jej w ten sposób.
źródło
-fPIE -no-pie
, zawsze byłby ładowany pod tym samym adresem, nawet gdyby mógł być połączony jako plik wykonywalny PIE. Używaćfile a.out
i szukaćELF executable
(non-PIE) vs. ELF współdzielony obiekt` (PIE): 32-bitowe adresy absolutne nie są już dozwolone w Linuksie x86-64?Po prostu użyj
file
na pliku binarnym:Zwróć uwagę na inny typ wydrukowany po informacji LSB.
źródło
executable
ishared object
. Zakładam, że wspólne obiekty muszą być relokowalne, dlatego moim zdaniem zostały skompilowane z SROKĄ.gcc -fPIE -pie
jest to teraz domyślne w wielu dystrybucjach.file
5.36 może teraz rozpoznawać SROKI w oparciu oDT_1_PIE
flagęDT_FLAGS_1
i wyraźnie mówipie executable
zamiastshared object
.file
5.36 mówi to wyraźniefile
5.36 faktycznie drukuje to wyraźnie, jeśli plik wykonywalny jest PIE, czy nie. Na przykład plik wykonywalny PIE pokazuje się jako:i inny niż SROKA, ponieważ:
Ta funkcja została wprowadzona w 5.33, ale wykonała jedynie prostą
chmod +x
kontrolę. Wcześniej drukowane tylkoshared object
dla SROKI.W 5.34 zamierzano rozpocząć sprawdzanie bardziej wyspecjalizowanych
DF_1_PIE
metadanych ELF, ale z powodu błędu w implementacji faktycznie coś zepsuło i pokazało pliki wykonywalne GIE PIE jakoshared objects
.Zinterpretowałem
file
kod źródłowy, w tym błąd, i dokładnie to, które bajty formatu ELF sprawdza on wyjątkowo szczegółowo pod adresem : https://stackoverflow.com/questions/34519521/hy-does-gcc-create-a-shared-object -in-zamiast-pliku wykonywalnego-binarnego zgodnie z / 55704865 # 55704865Szybkie podsumowanie zachowania pliku 5.36 to:
Elf32_Ehdr.e_type == ET_EXEC
executable
Elf32_Ehdr.e_type == ET_DYN
DT_FLAGS_1
jest obecny wpis sekcji dynamicznejDF_1_PIE
jest ustawiony wDT_FLAGS_1
:pie executable
shared object
pie executable
shared object
GDB uruchom plik wykonywalny dwa razy i zobacz ASLR
Jedną bardzo bezpośrednią rzeczą, którą możesz zrobić, jest dwukrotne uruchomienie pliku wykonywalnego za pośrednictwem GDB i sprawdzenie, czy adres zmienia się w różnych biegach z powodu ASLR.
Wyjaśniłem, jak to zrobić szczegółowo na stronie : https://stackoverflow.com/questions/2463150/what-is-the-fpie-option-for-position-independent-executables-in-gcc-and-ld/51308031 # 51308031
Chociaż niekoniecznie jest to najbardziej praktyczne rozwiązanie i nie jest możliwe, jeśli nie ufasz plikowi wykonywalnemu, jest zabawny i wykonuje ostateczną kontrolę, na której nam naprawdę zależy, to znaczy, czy jądro Linux / moduł ładujący dynamicznie zmienia lokalizację pliku wykonywalnego lub nie.
źródło
setarch -R
man7.org/linux/man-pages/man8/setarch.8.html „-R, --addr-no-randomize
Wyłącza randomizację wirtualnej przestrzeni adresowej. Włącza sięADDR_NO_RANDOMIZE
”. man7.org/linux/man-pages/man2/personality.2.html „ADDR_NO_RANDOMIZE
(od Linuksa 2.6.12) Po ustawieniu tej flagi wyłącz randomizację układu przestrzeni adresowej”.Na Github znajduje się skrypt bash checksec.sh do sprawdzania właściwości ograniczania plików wykonywalnych (w tym RELRO, Stack Canary, bit NX, PIE, RPATH, RUNPATH, Fortify Source).
Uruchom
checksec
z-f
argumentami (wprowadzanie pliku):źródło