アクセス権限のテスト
▹(access? path how) pathで指定されたファイルやディレクトリのアクセス権限(how)をテストします. 権限のテストは, この手続きを呼び出したプロセスの実ユーザーID・実グループIDに関して行います. path は,絶対パスか, カレントディレクトリを起点とする相対パスを表す文字列です. how は,確認したい権限を指定するフラグです. これは,以下に示す R_OK,W_OK,X_OK の組み合わせか, または F_OK のいずれかです.- R_OK 読み込み可能か否かをテストします.
- W_OK 書き込み可能か否かをテストします.
- X_OK 実行/探索が可能か否かをテストします.
- F_OK ファイルが存在するか否かをテストします.
$ guile GNU Guile 3.0.5 ...... 起動メッセージ ...... guile> (access? "/home/algo/tmp" R_OK) $1 = #t guile> (access? "/home/algo/tmp" (logior R_OK W_OK X_OK)) $2 = #t guile> (access? "./somefile.txt" (logior R_OK W_OK X_OK)) $3 = #f guile> (access? "/home/algo/tmp" F_OK) $4 = #t guile>
アクセス権限の変更
▹(chmod object mode)object によって指定されたファイルやディレクトリのアクセス権限(permission)を変更します. object は,ファイル名(文字列),ファイルポート,ファイルディスクリプタのいずれかを指定することができます. ただし,ポートやディスクリプタを使用する場合, ファイルはオープンしていなければいけません. mode は,アクセス権限を表す整数を指定します.これは, ターミナル(シェル)上のchmodコマンドの引数として指定する整数と同じものです. 一般に,その整数は,以下に示すフラグ(8進数)を加算した値です.
- #o0400 所有者に読み取りを許可する.
- #o0200 所有者に書き込みを許可する.
- #o0100 所有者に実行/探索を許可する.
- #o0040 所有グループに読み取りを許可する.
- #o0020 所有グループに書き込みを許可する.
- #o0010 所有グループに実行/探索を許可する.
- #o0004 他ユーザーに読み取りを許可する.
- #o0002 他ユーザーに書き込みを許可する.
- #o0001 他ユーザーに実行/探索を許可する.
- #o4000 Set-user-ID on execution.
- #o2000 Set-group-ID on execution.
- #o1000 sticky bit (On directories, restricted deletion flag)
$ guile GNU Guile 3.0.5 guile> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $1 = 0 guile> (chmod "/home/algo/tmp/somefile.txt" #o0755) guile> (system "ls -l /home/algo/tmp/somefile.txt") -rwxr-xr-x 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $2 = 0 guile> (chmod "/home/algo/tmp/somefile.txt" #o7755) guile> (system "ls -l /home/algo/tmp/somefile.txt") -rwsr-sr-t 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $3 = 0 guile>なお,sticky bit はディレクトリに設定して, そのディレクトリ内のファイルの削除や移動を制限するためのものです. 上の実行例が示すように,通常のファイルにも設定できますが意味をなしません.
所有権の変更
▹(chown object owner gourp)object によって指定されたファイルやディレクトリの所有者とグループを変更します.object が指定するファイルがシンボリックリンクだったとき, シンボリックリンクを辿った先のファイルの所有権を変更します. 残念ながら,現時点では,シンボリックリンクの所有権だけを変更する機能(システムコールのlchown関数の機能)はサポートされていません. object は,ファイル名を表す文字列です. 実行環境が fchown 関数をサポートしているならば, ファイルポートやファイルディスクリプタも指定できます. ただし,ポートやディスクリプタを指定する場合, そのファイルがオープンしていなければいけません. 筆者の環境(Debian 11)では, ポートやディスクリプタが使えるようです(下記の実行例を参照). owner と group は,それぞれ, ユーザーID(整数)とグループID(整数)です. ただし,-1 を指定したときには現在のIDを維持します(つまり,変更しません). ▹実行例:/home/algo/tmp/somefile.txt というファイルを対象に, その所有権を色々な方法で変更してみます. 所有権が変更されたことは system 手続きに ls コマンドを渡して確認します.system 手続きは,引数として渡されたコマンドをシェルの上で実行します(注:system 手続きの返り値は無視して下さい). それから.一般ユーザーは所有権の変更ができないので, スーパーユーザー権限でREPLを起動します.
$ sudo guile [sudo] algo のパスワード:*************************** ↵ GNU Guile 3.0.5 ...... 起動メッセージ ...... guile@root>まず,/home/algo/tmp/somefile.txt の現在の所有権(algo:algo)を確認します.
guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $1 = 0所有権をrootユーザー(root:root)に変更して,その結果を確認します.
guile@root> (chown "/home/algo/tmp/somefile.txt" 0 0) guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 root root 22 2月 3 21:02 /home/algo/tmp/somefile.txt $2 = 0somefile.txt をオープンしてファイルポートを作り, そのポートを使って所有権を元の状態(algo:algo)に戻します. 以下の 1000 はalgoのユーザーIDとグループIDです.
guile@root> (define port (open-input-file "/home/algo/tmp/somefile.txt")) guile@root> (chown port 1000 1000) guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $3 = 0さらに,ファイルポートからファイルディスクリプタを作って, ディスクリプタを使って所有権をrootユーザーに変更します. 以下の fileno は,ファイルポートからファイルディスクリプタを作るための手続きです.
guile@root> (define fd (fileno port)) guile@root> (chown fd 0 0) guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 root root 22 2月 3 21:02 /home/algo/tmp/somefile.txt $4 = 0最後に,所有者は変えずに,所有グループをalgo(IDは1000)に変更したあと, その結果を確認します. そのあとさらに,所有グループは変えずに, 所有者をalgo(IDは1000)に変更して,今回の実行例を終了します.
guile@root> (chown "/home/algo/tmp/somefile.txt" -1 1000) guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 root algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $5 = 0 guile@root> (chown "/home/algo/tmp/somefile.txt" 1000 -1) guile@root> (system "ls -l /home/algo/tmp/somefile.txt") -rw-r--r-- 1 algo algo 22 2月 3 21:02 /home/algo/tmp/somefile.txt $6 = 0▹実行例:シンボリックリンクに対して所有権を変更したときに何が起こるかを観察してみます.まず,somefile.txt と同じディレクトリ上に somefile.lnk というシンボリックリンクを作って,シンボリックリンクとファイルの所有権を確認します.
$ cd /home/algo/tmp $ ln -s somefile.txt somefile.lnk $ ls -l somefile.* lrwxrwxrwx 1 algo algo 12 2月 3 21:58 somefile.lnk -> somefile.txt -rw-r--r-- 1 algo algo 22 2月 3 21:02 somefile.txt次に, REPLの中でシンボリックリンク somefile.lnk の所有権をrootユーザーに変更したあと,リンクと元のファイルの所有権を確認してみます.
$ sudo guile [sudo] algo のパスワード: ********************************* ↵ GNU Guile 3.0.5 ...... 起動メッセージ ...... guile@root> (chown "/home/algo/tmp/somefile.lnk" 0 0) guile@root> (system "ls -l /home/algo/tmp/somefile.*") lrwxrwxrwx 1 algo algo 12 2月 3 21:58 /home/algo/tmp/somefile.lnk -> somefile.txt -rw-r--r-- 1 root root 22 2月 3 21:02 /home/algo/tmp/somefile.txt $1 = 0この結果を見ると,シンボリックリンクの所有権は変化せず, リンク先のファイルの所有権が変化しています.