Provided by: manpages-ja-dev_0.5.0.0.20210215+dfsg-1_all bug

名前

       unshare - プロセス実行コンテキストの一部を分離する

書式

       #include <sched.h>

       int unshare(int flags);

   glibc 向けの機能検査マクロの要件 (feature_test_macros(7)  参照):

       unshare():
           glibc 2.14 以降:
               _GNU_SOURCE
           glibc 2.14 より前:
               _BSD_SOURCE || _SVID_SOURCE
                   /* _GNU_SOURCE も定義される */

説明

       unshare()  を使うと、プロセスは他のプロセスと現在共有している 実行コンテキストの一部を分離
       することができる。 実行コンテキストの一部、たとえばマウント名前空間 (mount namespace)   な
       どは、新しいプロセスを  fork(2)  または vfork(2)  を使って生成したときに、暗黙のうちに共有
       される。 一方、仮想メモリーなどは、 clone(2)  を使ってプロセスを生成するときに、明示的に共
       有することを要求できる。

       unshare()  の主な利用法は、プロセスが新しいプロセスを生成することなく、 共有実行コンテキス
       トを制御することである。

       flags 引き数はビットマスクであり、 実行コンテキストのどの部分の共有を解除するかを表す。 こ
       の引き数は、以下の定数の 0 個以上の OR で指定する:

       CLONE_FILES
              clone(2)  CLONE_FILES フラグの効果を取り消す。 ファイルディスクリプターテーブルを共
              有させず、 呼び出し元プロセスは他のプロセスとファイルディスクリプターを共有しなくな
              る。

       CLONE_FS
              clone(2)  CLONE_FS フラグの効果を取り消す。ファイルシステム属性を共有させず、呼び出
              し元プロセスは、ルートディレクトリ  (chroot(2))、カレントディレクトリ  (chdir(2))、
              umask (umask(2)) を他のプロセスと共有しなくなる。

       CLONE_NEWIPC (Linux 2.6.19 以降)
              このフラグは clone(2) CLONE_NEWIPC フラグと同じ効果を持つ。 System V IPC 名前空間を
              共有せず、呼び出し元プロセスは 他のプロセスとは 共有しない固有の System V IPC  名前
              空間のコピーを持つ。 このフラグを指定 すると、 CLONE_SYSVSEM も暗黙のうちに指定され
              る。 CLONE_NEWIPC を 使用するには CAP_SYS_ADMIN ケーパビリティが必要である。

       CLONE_NEWNET (Linux 2.6.24 以降)
              このフラグは clone(2) CLONE_NEWNET フラグと同じ効果を持つ。ネット  ワーク名前空間を
              共有せず、呼び出し元プロセスは他のプロセスとは共有しな い固有のネットワーク名前空間
              のコピーを持つ。CLONE_NEWNET を使用する には CAP_SYS_ADMIN ケーパビリティが必要であ
              る。

       CLONE_NEWNS
              このフラグは  clone(2) CLONE_NEWNS フラグと同じ効果を持つ。 マウン ト名前空間を共有
              せず、呼び出し元プロセスは  他のプロセスとは共有しない固   有の名前空間のコピーを持
              つ。 このフラグを指定すると、 CLONE_FS も暗 黙のうちに指定される。 CLONE_NEWNS を使
              用するには CAP_SYS_ADMIN ケーパビリティが必要である。

       CLONE_NEWPID (Linux 3.8 以降)
              このフラグは clone(2) CLONE_NEWPID フラグと同じ効果を持つ。 PID  名前空間を共有しな
              い。 呼び出し元プロセスは、 すでに存在するどのプロセスとも共有されない新しい PID 名
              前空間を、 自身の子プロセス用に持つことになる。  このプロセスにより作成される最初の
              子プロセスはプロセス  ID 1 を持ち、 この新しい名前空間において init(1) の役割を持つ
              とみなされる。 CLONE_NEWPID を指定すると、自動的に CLONE_THREAD  も指定されたものと
              みなされる。 CLONE_NEWPID を使用するには CAP_SYS_ADMIN ケーパビリティが必要である。
              詳細な情報は pid_namespaces(7) を参照。

       CLONE_NEWUSER (Linux 3.8 以降)
              このフラグは clone(2) CLONE_NEWUSER フラグと同じ効果を持つ。 ユーザー名前空間を共有
              せず、 呼び出し元プロセスはすでに存在するどのプロセスとも共有されない新しいユーザー
              名前空間に移動される。 CLONE_NEWUSER フラグを指定して clone(2) で作成された子プロセ
              スと同様に、 呼び出し元は新しい名前空間ですべてのケーパビリティを獲得する。

              CLONE_NEWUSER  を使うには、呼び出し元プロセスがスレッド化されていないことが必要であ
              る。 CLONE_NEWUSER を指定すると、自動的に  CLONE_THREAD  が指定されたものとみなされ
              る。  Linux 3.9 以降では、 CLONE_NEWUSER が指定された場合 CLONE_FS も指定されたとみ
              なされる。 CLONE_NEWUSER を使うには、呼び出し元プロセスのユーザー ID とグループ  ID
              が、  呼び出した時点で、 呼び出し元プロセスのユーザー名前空間のユーザー ID とグルー
              プ ID にマッピングされている必要がある。

              ユーザー名前空間の詳細は user_namespaces(7) を参照。

       CLONE_NEWUTS (Linux 2.6.19 以降)
              このフラグは clone(2) CLONE_NEWUTS フラグと同じ効果を持つ。 UTS IPC  名前空間を共有
              せず、呼び出し元プロセスは他のプロセスとは共有しない  固有の  UTS  IPC 名前空間のコ
              ピーを持つ。     このフラグを指定すると、      CLONE_FS      も暗黙のうちに指定され
              る。CLONE_NEWUTS を使用するには CAP_SYS_ADMIN ケーパビリティが必要である。

       CLONE_SYSVSEM (Linux 2.6.26 以降)
              このフラグは  clone(2) CLONE_SYSVSEM フラグの効果を逆転させる。 System V セマフォの
              調整値 (semadj) を共有せず、 呼び出し元プロセスは他のプロセスとは共有されない新しい
              空の semadj リストを持つ。 そのプロセスが、自分の現在の semadj リストへの参照を持つ
              最後のプロセスであれば、 このリストの調整値は対応するセマフォに適用される (semop(2)
              に説明がある通り)。

       上記に加えて、  呼び出し元がシングルスレッドの場合 (すなわち別のプロセスやスレッドとアドレ
       ス空間を共有していない場合)、 CLONE_THREAD, CLONE_SIGHAND,  CLONE_VM  を指定することができ
       る。   この場合、   これらのフラグは効果を持たない。   (CLONE_THREAD  を指定すると自動的に
       CLONE_VM が指定されたとみなされ、 CLONE_VM を指定すると自動的に CLONE_SIGHAND が指定された
       とみなされる点に注意してほしい。)  プロセスがマルチスレッドの場合、 これらのフラグを使用す
       るとエラーとなる。

       flags に 0 が指定された場合、 unshare()  は何も行わないので、 呼び出し元プロセスの実行コン
       テキストは、何も変更されない。

返り値

       成功した場合は  0 が返される。 失敗した場合は -1 が返されて、 errno にはエラーを示す値が設
       定される。

エラー

       EINVAL flags に不正なビットが指定された。

       EINVAL CLONE_THREAD, CLONE_SIGHAND, CLONE_VMflags に指定されたが、  呼び出したプロセス
              はマルチスレッドである。

       ENOMEM 呼び出し元のコンテキストのうち共有を解除する必要がある部分をコピーするために、 十分
              なメモリーが確保できなかった。

       EPERM  呼び出し元プロセスはこの操作を行うのに必要な特権を持っていなかった。

       EPERM  CLONE_NEWUSERflags に指定されたが、 呼び出し元の実効ユーザー ID  もしくは実効グ
              ループ ID が親名前空間にマッピングがない (user_namespaces(7) 参照)。

       EPERM (Linux 3.9 以降)
              CLONE_NEWUSERflags  に指定され、 呼び出し元が chroot された環境にいる (すなわ
              ち、呼び出し元の root ディレクトリが呼び出し元が属するマウント名前空間の root  ディ
              レクトリに一致しない)。

       EUSERS (Linux 3.11 以降)
              CLONE_NEWUSERflags に指定されており、 この呼び出しによりネストされたユーザー名
              前空間数の上限を超えてしまう。 user_namespaces(7) を参照。

バージョン

       unshare()  システムコールは Linux カーネル 2.6.16 で追加された。

準拠

       unshare()  システムコールは Linux 固有である。

注意

       clone(2)   で新しいプロセスを生成したときに共有される全てのプロセス属性を、  unshare()  に
       よって共有の解除ができるわけではない。   特に、カーネル   3.8   時点では、  unshare()   に
       CLONE_SIGHAND, CLONE_THREAD, CLONE_VM の効果を取り消すためのフラグが実装されていない。  こ
       れらの機能は、必要であれば将来追加されるかもしれない。

       以下のプログラムは  unshare(1) コマンドの簡単な実装である。 このコマンドは、1 つ以上の名前
       空間の unshare を行ってから、 コマンドライン引き数で指定されたコマンドを実行する。  以下は
       このプログラムの使用例である。 新しいマウント名前空間でシェルを実行し、 元のシェルと新しい
       シェルが別のマウント名前空間にいることを確認している。

           $ readlink /proc/$$/ns/mnt
           mnt:[4026531840]
           $ sudo ./unshare -m /bin/bash
           [sudo] password for cecilia:
           # readlink /proc/$$/ns/mnt
           mnt:[4026532325]

       2 つの readlink(1) コマンドの出力が違うことから、 2 つのシェルは異なるマウント名前空間にい
       ることが分かる。

   プログラムのソース

       /* unshare.c

          A simple implementation of the unshare(1) command: unshare
          namespaces and execute a command.
       */
       #define _GNU_SOURCE
       #include <sched.h>
       #include <unistd.h>
       #include <stdlib.h>
       #include <stdio.h>

       /* A simple error-handling function: print an error message based
          on the value in 'errno' and terminate the calling process */

       #define errExit(msg)    do { perror(msg); exit(EXIT_FAILURE); \
                               } while (0)

       static void
       usage(char *pname)
       {
           fprintf(stderr, "Usage: %s [options] program [arg...]\n", pname);
           fprintf(stderr, "Options can be:\n");
           fprintf(stderr, "    -i   unshare IPC namespace\n");
           fprintf(stderr, "    -m   unshare mount namespace\n");
           fprintf(stderr, "    -n   unshare network namespace\n");
           fprintf(stderr, "    -p   unshare PID namespace\n");
           fprintf(stderr, "    -u   unshare UTS namespace\n");
           fprintf(stderr, "    -U   unshare user namespace\n");
           exit(EXIT_FAILURE);
       }

       int
       main(int argc, char *argv[])
       {
           int flags, opt;

           flags = 0;

           while ((opt = getopt(argc, argv, "imnpuU")) != -1) {
               switch (opt) {
               case 'i': flags |= CLONE_NEWIPC;        break;
               case 'm': flags |= CLONE_NEWNS;         break;
               case 'n': flags |= CLONE_NEWNET;        break;
               case 'p': flags |= CLONE_NEWPID;        break;
               case 'u': flags |= CLONE_NEWUTS;        break;
               case 'U': flags |= CLONE_NEWUSER;       break;
               default:  usage(argv[0]);
               }
           }

           if (optind >= argc)
               usage(argv[0]);

           if (unshare(flags) == -1)
               errExit("unshare");

           execvp(argv[optind], &argv[optind]);
           errExit("execvp");
       }

関連項目

       unshare(1), clone(2), fork(2), kcmp(2), setns(2), vfork(2), namespaces(7)

       Linux カーネルソース内の Documentation/unshare.txt

この文書について

       この  man ページは Linux man-pages プロジェクトのリリース 3.79 の一部 である。プロジェクト
       の説明とバグ報告に関する情報は http://www.kernel.org/doc/man-pages/ に書かれている。