ACLはLinuxでファイル権限をオーバーライドできますか?

ACLはLinuxでファイル権限をオーバーライドできますか?

私は最近FreeBSDでこの問題に直面しましたが、ZFSがこの問題を解決するのを助けてくれてありがとう。しかし、CentOSでext4を使用してこの問題に再会し、それをバイパスする簡単な方法(またはバイパスする方法)があるかどうか疑問に思いました。私が望むのは、ユーザーの無効性umask、誤ったFTPクライアントのアップロードの決定などに関係なく、特定のグループのすべてのユーザーにファイルへの読み取り/書き込みアクセスが保証されるディレクトリです。私はこれが可能だとは思わないが、間違って欲しい。これが不可能に見えるのは、ext4 ACLがファイル権限をオーバーライドできず、交差することしかできないためです。たとえば、

# mkdir bar
# chmod 700 bar
# getfacl bar
# file: bar
# owner: root
# group: mygroup
# flags: -s-
user::rwx
group::rwx                      #effective:---
group:mygroup:rwx              #effective:---
mask::---
other::---
default:user::rwx
default:group::rwx
default:group:mygroup:rwx
default:mask::rwx
default:other::---

デフォルトのACLを表示できます。そしてrwxマスクは両方に指定されますが、ファイルmygroup権限がこれより優先されるため、---これは、ユーザーのFTPクライアント(たとえば)がファイルを640にアップロードした場合、グループの他の人がそれを妨げることができないことを意味します。解決策はありますか?

答え1

ACLによって付与された権限はい追加的ですが、再帰的であると予想しましたか? (彼らはそうではありません)

ACLを使用すると、あなたが望むものをほとんど得ることができます。まず、上記のようにACLを設定する必要があります。再帰的ツリー内のすべてのファイルとディレクトリ。default:group:mygroup:rwxディレクトリの設定を含める必要があります。すべての新しいディレクトリには、そのディレクトリ内の新しいファイルと同様に、これらの設定が自動的に適用されます。

2つはまだ失敗しました。

  • 誰かがツリーの外からファイルやディレクトリを移動するとき。 inodeがすでに存在するため、デフォルト値は設定されません。
  • 誰かがACL認識プログラムを使用してアーカイブからファイルを抽出すると、プログラムはデフォルト値を上書きします。

定期的に実行されるようにクローンジョブを作成する以外に、これら2つの問題を処理する方法はありませんchgrp -R mygroup DIRECTORY; chmod g+rwx -R DIRECTORY。これは、共有ディレクトリ内のファイルの数によっては実用的でもそうでない場合もあります。

これは、ファイルツリーでACLを変更するために使用するスクリプトを少し変更したバージョンです。特定の読み取り/書き込みおよび読み取り専用グループのリストを含むツリー内のすべてのエントリに対してACLを完全に上書きします。

#! /usr/bin/env perl
use strict;
use warnings;
use String::ShellQuote;
use Cwd 'abs_path';

# Usage: fix-permissions.pl DIRECTORY RW_GROUP1,RW_GROUP2... RO_GROUP1,RO_GROUP2...

my $dir= $ARGV[0];
my @rw_groups= split ',', $ARGV[1] if $ARGV[1];
my @ro_groups= split ',', $ARGV[2] if $ARGV[2];
-d $dir or die "No such directory'$dir'\n";
$dir= abs_path($dir);
$dir =~ m|/[^/]+/| or die "Cowardly refusing to run on a top-level directory: $dir\n";

# Give all files rw-r----- and all directories rwxr-x---
# then give each rw_group read/write access, then each ro_group
# read-only access to the whole tree
my $dir_perm= join(',',
  'u::rwx',
  'g::r-x',
  'o::---',
  'd:u::rwx',
  'd:g::r-x',
  'd:o::---',
  ( map { "g:$_:rwx" } @rw_groups ),
  ( map { "d:g:$_:rwx" } @rw_groups ),
  ( map { "g:$_:r-x" } @ro_groups ),
  ( map { "d:g:$_:r-x" } @ro_groups )
);
my $file_perm= join(',',
  'u::rwx',
  'g::r-x',
  'o::---',
  ( map { "g:$_:rw-" } @rw_groups ),
  ( map { "g:$_:r--" } @ro_groups )
);

for (
  "find ".shell_quote($dir)." -type d -print0 | xargs -0 -r setfacl --set ".shell_quote($dir_perm),
  "find ".shell_quote($dir)." ! -type d -print0 | xargs -0 -r setfacl --set ".shell_quote($file_perm)
) {
  0 == system($_) or die "command failed: $_\n";
}

関連情報