2016-08-23 14 views
1

私はsshfsで/を使ってディレクトリをマウントするためにユーザが呼び出せるプログラムを書いています。エラー処理と定型句が省略された基本レイアウトは次のとおりです。子プロセスはrootにseteuidする必要があります、親はありません

uid_t euid, ruid; 

void mountDir(char *dirname, char *hostname){ 
    childPid = fork(); 
    if(childPid == 0){ 
     char *sshfsArgs[6] = {"/usr/bin/sshfs", hostName, /*Other args*/}; 
     seteuid(euid); 
     execv(sshfsArgs[0], sshfsArgs); 
     //I want to drop my setuid permissions with seteuid(ruid), 
     //but execv doesn't return. 
    }else{ //I'm the parent process. 
     //I don't want to have root permissions now. 
     wait(childPid); 
    } 
} 


void main(int argc, char **argv){ 
    ruid = getuid(); 
    euid = geteuid(); 
    seteuid(ruid); //Drop the root permissions. 
    char **hostList = {"bulb.example.com", "char.example.com", argv[1]}; 
    char * hostName = pickHost(hostList); //Pings them and picks one that responds. 
    mountDir("/net/home", hostName); 
    mountDir("/net/projects", hostName); 
} 

ここでもまた、多量のエラーチェックは省略されています。私はsshfsを実行しているときにのみroot権限を持ちたいと思っています。 fork()を呼び出す前にseteuid特権を落とすいくつかの例がありますが、ここではそれらを子プロセスでのみ取得し、execvの直後に失いたいと考えています。これをどうやって安全に行うのですか?子プロセスがルートにseteuidを実行するとどうなりますか?親プロセスはこれまでにroot権限を取得していますか?

答えて

2

これを現在処理している方法は正しいです。

プロセスが最初に行うことは、ルート権限を削除することです。その時点で安全です。

forkの後、親は子を待ち、子はseteuid(euid);を実行します。そのため、子は今ではroot権限で実行されています(それはseteuidが実行されているためです)が、親は実行されていません。その後、子供はexecvを呼び出してsshfsをroot権限で実行します。

seteuid子コールは、別のプロセス(execvより前に同じコードを実行しているにもかかわらず)であるため、親には影響しません。

execvが返されないため、再度権限を削除する必要はありません。 sshfsが終了すると、そのプロセスは終了します。 execvが失敗した場合は、_exitを呼び出す前に特権を削除し、エラーメッセージを出力します。

関連する問題