Mam proces, który zaczyna się od damona działającego jako root, teraz chcę „obniżyć” uprawnienia tego procesu do uprawnień przeciętnego użytkownika. czy to możliwe? Jeśli tak jak?
PS: Uruchamianie unixa na komputerze Mac
Mam proces, który zaczyna się od damona działającego jako root, teraz chcę „obniżyć” uprawnienia tego procesu do uprawnień przeciętnego użytkownika. czy to możliwe? Jeśli tak jak?
PS: Uruchamianie unixa na komputerze Mac
Odpowiedzi:
Sam proces musi wywoływać setuid (2). Powinieneś także zbadać uruchomienie go w chroot (8), jeśli jeszcze tego nie zrobiłeś. O ile mi wiadomo, root nie może zmienić UID innego procesu.
Jeśli powodem, dla którego uruchamiasz go jako root, jest powiązanie portów, sugerowałbym uruchomienie go jako normalnego użytkownika na wyższym porcie i użycie ipfw (8) w OS X do przekazania portu 80/443 / etc na wyższy port:
http://support.crashplanpro.com/doku.php/recipe/forward_port_443_to_pro_server_on_mac_osx
setuid()
samo dzwonienie absolutnie nie wystarczy.
sudo tcpdump -Z
używa initgroups (3), setgid (2) i setuid (2), aby usunąć uprawnienia root'a do własnego procesu.
# code taken from:
# http://www.opensource.apple.com/source/tcpdump/tcpdump-32/tcpdump/tcpdump.c
/* Drop root privileges and chroot if necessary */
static void
droproot(const char *username, const char *chroot_dir)
{
...
if (initgroups(pw->pw_name, pw->pw_gid) != 0 ||
setgid(pw->pw_gid) != 0 || setuid(pw->pw_uid) != 0) {
fprintf(stderr, "tcpdump: Couldn't change to '%.32s' uid=%lu gid=%lu: %s\n",
username,
(unsigned long)pw->pw_uid,
(unsigned long)pw->pw_gid,
pcap_strerror(errno));
exit(1);
}
...
}
initgroups
, setgid
, setuid
(Wreszcie!) Jest właśnie prawo paradygmat UNIX, i zawsze powinny być przestrzegane. Ponadto odpowiedzialna funkcja „droproot” sprawdza, czy jej identyfikator uid i gid rzeczywiście zostały ustawione, nawet jeśli wszystkie trzy podstawowe funkcje zwróciły sukces.
Możesz uruchamiać polecenia tak, jak inni użytkownicy, używając su
:
su USERNAME -c COMMAND
Będzie działać COMMAND
z upuszczonymi uprawnieniami USER
.
Zauważ, że domyślnie su
do interpretacji polecenia użyje interpretera powłoki docelowego użytkownika. Natomiast domyślnym zachowaniem sudo
jest traktowanie programu COMMAND
jako samodzielnego programu, czyli bieżącego środowiska. Oczywiście te domyślne zachowania można zmienić za pomocą różnych przełączników i zmiennych środowiskowych.
su
że nie działa, jeśli USERNAME nie ma zdefiniowanej powłoki (lub /bin/false
), podczas gdy sudo działa.
su
to odzwierciedli. Jednak zawsze można to zmienić za pomocą -s
przełącznika. Zauważ, że celem su
jest naśladowanie zachowania danego użytkownika - na co zwykle ma wpływ jego / jej powłoka. Z drugiej strony sudo
(domyślnie) zignoruje ustawienie powłoki docelowego użytkownika.
Aby upuścić uprawnienia, musisz mieć uprawnienia użytkownika innego niż root. Następnie wystarczy przejść do tego użytkownika:
#define UNPRIV_UID 48
#define UNPRIV_GID 48
if (getuid() == 0) { // we are root
// setting UID/GID requires root privileges, so if you don't set
// the GID first, you won't be able to do it at all.
if (setgid(UNPRIV_GID)!=0) die("Failed to set nonroot GID");
if (setuid(UNPRIV_UID)!=0) die("Failed to set nonroot UID");
}
ASSERT(getuid() != 0);
Zauważ, że odbywa się to w samym programie , a nie w skrypcie opakowania. Wiele programów wymaga uprawnień roota do określonego celu (np. Do połączenia z portem o niskim numerze), ale potem nie potrzebuje roota. Programy te będą więc uruchamiać się jako root, a następnie upuszczać uprawnienia, gdy nie będą już potrzebne.
Jeśli w ogóle nie potrzebujesz uprawnień roota, po prostu nie uruchamiaj go jako root. Na przykład:
# Change this:
myprog -C /my/config/file
# To this:
sudo -u someuser myprog -C /my/config/file
# Or this
su someuser -c "myprog -C /my/config/file"
setuid
Funkcja ustawia tylko efektywne UID, a nie rzeczywisty UID. Powinieneś użyć, setreuid
jeśli nie chcesz, aby proces mógł odzyskać uprawnienia. (A powyższy kod nie dotyczy również dodatkowych uprawnień grupowych. Jest odpowiedni tylko do uruchamiania najbardziej zaufanego kodu.)
setuid()
ustawia rzeczywiste i zapisane identyfikatory użytkownika; możesz myśleć seteuid()
. Nie wszystkie systemy mają setreuid()
, więc nie można go używać wszędzie. Dokładna semantyka setuid()
jest skomplikowana, ale jeśli masz euid 0, będziesz w stanie porzucić wszystkie tradycyjne uprawnienia identyfikatora użytkownika setuid()
. Największym pominięcie w tej odpowiedzi jest to, że initgroups
albo setgroups
musi zostać wywołana, jak setgid
i setuid
, i że bardziej wnikliwe twierdzenia powinny być wykonywane na końcu.
Jeśli wykonujesz inny plik wykonywalny, np. Wywołujesz execve
lub inną exec
rodzinę funkcji, być może pośrednio przez funkcję taką jak system
lub popen
, a proces potomny powinien działać bez uprawnień od samego początku, najprostszym sposobem jest uzyskanie zaangażowana powłoka i zadzwoń su
. Oto przegląd tego, jak może wyglądać kod w Perlu, wraz z cytowaniem potrzebnym do:
$shell_command = quotemeta($path_to_executable) . " --option";
$shell_command =~ s/'/'\\''/; # protect single quotes for the use as argument to su
$su_command = sprintf("su -c '%s' %s", $shell_command, quotemeta($user_name));
open(PIPE, "$su_command |") or die;
Jeśli proces potomny musi zostać uruchomiony jako root, ale później upuść uprawnienia, zapoznaj się z kodem w tej odpowiedzi , który ilustruje sposób obniżenia uprawnień w procesie.