Korzystanie z CmndAlias ALL
nigdy nie będzie bezpieczne
Istnieje 1000 sposobów na uruchomienie service network restart
bez robienia sudo service network restart
. Oto przykład tego, co niegrzeczny użytkownik może spróbować:
$ echo "service network restart" > /tmp/hax
$ chmod a+x /tmp/hax
$ sudo /tmp/hax
Jeśli podasz użytkownikom ALL
alias polecenia, a następnie spróbujesz utworzyć czarną listę, zawsze będą w stanie ją obejść. Czarna lista bash, a oni będą używać Pythona. Python z czarnej listy, a oni użyją Perla. Perl z czarnej listy, a oni będą używać PHP. Nikt tego nie chce!
Jeśli naprawdę nie chcesz, aby ktoś coś zrobił, powinieneś zrobić, jak mówi Thomas, i utworzyć białą listę rzeczy, które mogą robić.
Konfigurowanie białej listy z wyjątkiem
Przykład małej białej listy z wykluczeniem można znaleźć u dołu man sudoers
:
pete HPPA = /usr/bin/passwd [A-Za-z]*, !/usr/bin/passwd root
The user pete is allowed to change anyone's password except for root on the HPPA
machines. Note that this assumes passwd(1) does not take multiple user names
on the command line.
(W rzeczywistości ten przykład ze strony podręcznika jest niebezpieczny i można go wykorzystać do zmiany hasła roota! Zobacz komentarze poniżej).
Możemy starać się przystosować, że w Twoim przypadku, aby oferować wszystkie service
polecenia do grupy pracowników, ale wyklucza te service network
polecenia, które dotyczą Ciebie:
%staff ALL = /usr/sbin/service *, \
! /usr/sbin/service *network*, \
! /usr/sbin/service *NetworkManager*
(Ta ALL
pozycja odnosi się do Host_Alias, a nie do Cmnd_Alias - mylące, prawda?)
Użytkownik nie będzie mógł uruchomić sudo bash
lub sudo tee
lub sudo wget
lub sudo /path/to/malicious_script
. Jeśli zachowasz ostrożność, możesz dodać do białej listy więcej poleceń administratora dla swoich użytkowników. Po prostu bądź konkretny!
Uwaga: dodałem *
przed słowem network
powyżej, na wypadek, gdyby service
w przyszłości do narzędzia dodano niegroźną flagę . Wyobraźmy sobie, że --verbose
flaga zostanie dodana w przyszłości, a następnie użytkownicy będą mogli uruchomić następujące funkcje:
$ sudo service --verbose network restart
Musimy więc *
użyć flag przed nazwą usługi. Jedyną wadą jest to, że może to blokować inne usługi, które nie mają nic przeciwko działającym użytkownikom, np. Usługa o nazwie safe-network
lub network-monitor
też zostanie odrzucona.
Pozwól użytkownikom edytować plik przy użyciu uprawnień grupy
Poniżej można znaleźć różne próby użycia rnano
za pomocą, sudo
aby umożliwić użytkownikom edycję pliku lub plików. Ale tak naprawdę są bardziej złożone i bardziej niebezpieczne niż powinny.
Dużo prostszym i bezpieczniejszym rozwiązaniem jest zmiana uprawnień grupy do określonych plików, dla których chcesz otworzyć uprawnienia do edycji. Oto kilka przykładów:
### Give steve the ability to edit his nginx config:
$ chgrp steve /etc/nginx/sites-available/steves_dodgy_project
$ chmod g+rw /etc/nginx/sites-available/steves_dodgy_project
### Let all members of the staff group edit the group_website config:
$ chgrp staff /etc/nginx/sites-available/group_website
$ chmod g+rw /etc/nginx/sites-available/group_website
Jeśli potrzebujesz bardziej szczegółowej kontroli (na przykład: dostęp tylko dla 3 użytkowników, ale nie dla wszystkich pracowników), możesz utworzyć nową grupę za pomocą addgroup
polecenia i dodać do niej tylko kilku użytkowników.
Pozwól użytkownikom edytować plik sudo
Pozostała część tej odpowiedzi stała się badaniem, jak łatwo jest pozostawić dziury w sudo
konfiguracji, próbując zaoferować użytkownikom elastyczność. Nie polecam robienia żadnej z poniższych czynności!
Jeśli chcesz przyznać użytkownikom dostęp do edycji określonego pliku, możesz spróbować użyć rnano
:
%staff ALL = /bin/rnano /etc/nginx/sites-available/host
rnano
pozwoli im tylko edytować określony plik. Jest to ważne, aby uniemożliwić złośliwemu użytkownikowi edytowanie innej usługi upstart (na przykład /etc/init.d/urandom
) i dodawanie do niej wiersza, który byłby uruchomiony service network restart
.
Niestety nie znalazłem sposobu na rvim
wystarczające ograniczenie (użytkownik może nadal otwierać dowolny plik za pomocą :e
), więc utknęliśmy nano
.
Niestety umożliwienie użytkownikom edycji wielu plików jest znacznie trudniejsze ...
Pozwól użytkownikom edytować wiele plików (znacznie trudniejsze niż powinno)
1. Niebezpieczne podejścia
Uważaj na symbole wieloznaczne! Jeśli oferujesz zbyt dużą elastyczność (lub dowolną), możesz ją wykorzystać:
%staff ALL = /bin/rnano /etc/nginx/sites-available/* # UNSAFE!
W takim przypadku złośliwy użytkownik będzie mógł edytować dowolny inny skrypt usługi wstępnej, a następnie uruchomić go:
$ sudo rnano /etc/nginx/sites-available/../../../any/file/on/the/system
(Sudo faktycznie uniemożliwia .
i ..
rozwija polecenie, ale niestety nie argumenty.)
Miałem nadzieję, że coś takiego może zadziałać, ale nadal nie jest pewne:
%staff ALL = /bin/rnano /etc/nginx/sites-available/[A-Za-z0-9_-]* # UNSAFE!
Ponieważ sudo
obecnie oferuje tylko globalne wzorce, które *
będą pasować do wszystkiego - nie jest to wyrażenie regularne!
(Edycja: I uznała, jeśli może uciec z powyższym w sytuacji, ponieważ nie istnieją żadne podfoldery znajdujące się pod sites-available
. Zrobiliśmy popyt jeden char być dopasowane po folderze, a /..
. Nie uda po nazwie pliku Jednak nie jest to wykonalne rozwiązanie, ponieważ rnano
akceptuje wiele argumentów. W każdym razie nadal byłoby to niebezpieczne w przypadku folderu zawierającego podfoldery!)
Nawet jeśli nie mamy podfolderów i nie uwzględniamy żadnych wierszy zawierających /../
, reguła oferująca *
glob może być nadal wykorzystywana, ponieważ rnano
akceptuje wiele argumentów ( <C-X>
przełączanie się między nimi , a przestrzeń jest chętnie akceptowana przez *
glob).
$ rnano /etc/nginx/sites-available/legal_file /then/any/file/on/the/system
2. Pchanie koperty (również ostatecznie niebezpieczne)
A co jeśli odrzucimy dowolne wiersze zawierające spacje lub spróbujemy dotrzeć /..
? Wtedy ostatecznym wykonalnym rozwiązaniem może być:
# I tried hard to make this safe, but in the end I failed again.
# Please don't use this unless you are really smart or really stupid.
%staff ALL = /bin/rnano /etc/nginx/sites-available/*, \
! /bin/rnano */..*, \
! /bin/rnano /etc/nginx/sites-available/, \
! /bin/rnano */., \
! /bin/rnano * *
# CONCLUSION: It is still NOT SAFE if there are any subfolders, due to
# the bug in rnano described below.
Przyjmujemy wszystko „pod” w folderze, ale także odrzucić wszelkie wywołanie rnano
czy /..
lub /.
czy
są przekazywane, lub jeśli folder jest kierowane bezpośrednio. (Technicznie /.
wykluczenie sprawia, że /..
wykluczenie jest zbędne, ale pozostawiłem oba dla jasności).
Znalazłem folder i /.
wyjątki były potrzebne, ponieważ w przeciwnym razie użytkownik mógłby skierować folder na sam folder. Teraz możesz pomyśleć, rnano
że zablokuje się, jeśli wskażesz na folder, ale pomylisz się. W rzeczywistości moja wersja (2.2.6-1ubuntu1) uruchamia się z łagodnym ostrzeżeniem i pustym plikiem, a następnie <C-X>
prosi mnie o podanie nazwy pliku, w którym chcę zapisać, otwierając nowy wektor ataku! Cóż, przynajmniej odmówił zastąpienia istniejącego pliku (w jednym teście, który zrobiłem). W każdym razie, ponieważ nie ma sposobu na umieszczenie podfolderów na czarnej liście w sudo, musimy stwierdzić, że takie podejście jest znowu niebezpieczne. Przepraszamy użytkowników!
To odkrycie sprawiło, że wątpię w dokładność nano
trybu „ograniczonego”. Mówią, że łańcuch jest tak silny, jak jego najsłabsze ogniwo. Zaczynam odczuwać połączenie sudo
czarnej listy z czarną magią i rnano
może nie być bardziej bezpieczny niż łańcuch stokrotek.
3. Bezpieczne, ale ograniczone podejścia
Globy są bardzo ograniczone - nie pozwalają nam wielokrotnie dopasowywać klasy postaci. Państwo mogli zaoferować wiele edycje pliku, jeśli wszystkie nazwy plików mają taką samą długość (w tym przypadku host
następuje jednej cyfry):
%staff ALL = /bin/rnano /etc/nginx/sites-available/host[0-9] # SAFE
Ale jeśli chcesz dać użytkownikowi dostęp do edycji różnych plików, konieczne może być jawne określenie każdego z nich:
%staff ALL = /bin/rnano /etc/nginx/sites-available/hothost \
/bin/rnano /etc/nginx/sites-available/coldhost \ # SAFE
/bin/rnano /etc/nginx/sites-available/wethost \
/bin/rnano /etc/nginx/sites-available/steves_dodgy_project
Nie daj się skusić na użycie*
w żadnym momencie. Dlaczego? Zobacz sekcje 1. i 2. powyżej! Pamiętaj: jeden mały poślizg może narazić na szwank całe konto administratora i cały system.
4. Napisz własny moduł do sprawdzania argumentów (bezpieczeństwo jest teraz Twoim obowiązkiem)
Mam nadzieję, że dodadzą obsługę wyrażeń regularnych sudo
w przyszłości; może poprawnie rozwiązać wiele problemów. Ale możemy również potrzebować możliwości sprawdzenia właściwości argumentów (aby zezwolić tylko na pliki, tylko foldery lub tylko niektóre flagi).
Ale istnieje jedna alternatywa dla stworzenia elastyczności w sudo. Zwalać odpowiedzialność:
%staff ALL = /root/bin/staffedit *
Następnie napisz własny staffedit
skrypt lub plik wykonywalny, aby sprawdzić, czy argumenty przekazane przez użytkownika są zgodne z prawem, i zrealizuj ich żądanie tylko wtedy, gdy są.
networking
inetwork-manager
? Ponadto, dlaczego Twoi użytkownicy mająsudo
dostęp? Nie powinny, chyba że chcesz, aby mieli pełne uprawnienia root.