Pretty comprehensive ACL tests.
This must be run on a filesystem with ACL support. Also, you will need
two dummy users (bin and daemon) and a dummy group (daemon).
$ rm -f f
$ umask 027
$ touch f
Only change a base ACL:
$ chacl u::rw,g::r,o::- f
$ setfacl -m u::r f
$ setfacl -m u::rw,u:bin:rw f
$ ls -dl f | awk '{print $1}'
> -rw-rw----+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> group::r--
> mask::rw-
> other::---
>
$ rm f
$ umask 022
$ touch f
$ setfacl -m u:bin:rw f
$ ls -dl f | awk '{print $1}'
> -rw-rw-r--+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> group::r--
> mask::rw-
> other::r--
>
$rm f
$ umask 027
$ mkdir d
$ setfacl -m u:bin:rwx d
$ ls -dl d | awk '{print $1}'
> drwxrwx---+
$ getfacl --omit-header d
> user::rwx
> user:bin:rwx
> group::r-x
> mask::rwx
> other::---
>
$ rmdir d
$ umask 022
$ mkdir d
$ setfacl -m u:bin:rwx d
$ ls -dl d | awk '{print $1}'
> drwxrwxr-x+
$ getfacl --omit-header d
> user::rwx
> user:bin:rwx
> group::r-x
> mask::rwx
> other::r-x
>
$ rmdir d
Multiple users
$ umask 022
$ touch f
$ setfacl -m u:bin:rw,u:daemon:r f
$ ls -dl f | awk '{print $1}'
> -rw-rw-r--+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> user:daemon:r--
> group::r--
> mask::rw-
> other::r--
>
Multiple groups
$ setfacl -m g:users:rw,g:daemon:r f
$ ls -dl f | awk '{print $1}'
> -rw-rw-r--+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> user:daemon:r--
> group::r--
> group:daemon:r--
> group:users:rw-
> mask::rw-
> other::r--
>
Remove one group
$ setfacl -x g:users f
$ ls -dl f | awk '{print $1}'
> -rw-rw-r--+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> user:daemon:r--
> group::r--
> group:daemon:r--
> mask::rw-
> other::r--
>
Remove one user
$ setfacl -x u:daemon f
$ ls -dl f | awk '{print $1}'
> -rw-rw-r--+
$ getfacl --omit-header f
> user::rw-
> user:bin:rw-
> group::r--
> group:daemon:r--
> mask::rw-
> other::r--
>
$ rm f
Default ACL
$ umask 027
$ mkdir d
$ setfacl -m u:bin:rwx,u:daemon:rw,d:u:bin:rwx,d:m:rx d
$ ls -dl d | awk '{print $1}'
> drwxrwx---+
$ getfacl --omit-header d
> user::rwx
> user:bin:rwx
> user:daemon:rw-
> group::r-x
> mask::rwx
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
Umask now ignored?
$ umask 027
$ touch d/f
$ ls -dl d/f | awk '{print $1}'
> -rw-r-----+
$ getfacl --omit-header d/f
> user::rw-
> user:bin:rwx #effective:r--
> group::r-x #effective:r--
> mask::r--
> other::---
>
$ rm d/f
$ umask 022
$ touch d/f
$ ls -dl d/f | awk '{print $1}'
> -rw-r-----+
$ getfacl --omit-header d/f
> user::rw-
> user:bin:rwx #effective:r--
> group::r-x #effective:r--
> mask::r--
> other::---
>
$ rm d/f
Default ACL copying
$ umask 000
$ mkdir d/d
$ ls -dl d/d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/d
> user::rwx
> user:bin:rwx #effective:r-x
> group::r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
$ rmdir d/d
$ umask 022
$ mkdir d/d
$ ls -dl d/d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/d
> user::rwx
> user:bin:rwx #effective:r-x
> group::r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
Add some users and groups
$ setfacl -nm u:daemon:rx,d:u:daemon:rx,g:users:rx,g:daemon:rwx d/d
$ ls -dl d/d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/d
> user::rwx
> user:bin:rwx #effective:r-x
> user:daemon:r-x
> group::r-x
> group:daemon:rwx #effective:r-x
> group:users:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:user:daemon:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
Symlink in directory with default ACL?
$ ln -s d d/l
$ ls -dl d/l | awk '{print $1}' | sed 's/\\.$//g'
> lrwxrwxrwx
$ ls -dl -L d/l | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/l
> user::rwx
> user:bin:rwx #effective:r-x
> user:daemon:r-x
> group::r-x
> group:daemon:rwx #effective:r-x
> group:users:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:user:daemon:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
$ rm d/l
Does mask manipulation work?
$ setfacl -m g:daemon:rx,u:bin:rx d/d
$ ls -dl d/d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/d
> user::rwx
> user:bin:r-x
> user:daemon:r-x
> group::r-x
> group:daemon:r-x
> group:users:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx #effective:r-x
> default:user:daemon:r-x
> default:group::r-x
> default:mask::r-x
> default:other::---
>
$ setfacl -m d:u:bin:rwx d/d
$ ls -dl d/d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d/d
> user::rwx
> user:bin:r-x
> user:daemon:r-x
> group::r-x
> group:daemon:r-x
> group:users:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:rwx
> default:user:daemon:r-x
> default:group::r-x
> default:mask::rwx
> default:other::---
>
$ rmdir d/d
Remove the default ACL
$ setfacl -k d
$ ls -dl d | awk '{print $1}'
> drwxrwx---+
$ getfacl --omit-header d
> user::rwx
> user:bin:rwx
> user:daemon:rw-
> group::r-x
> mask::rwx
> other::---
>
Reset to base entries
$ setfacl -b d
$ ls -dl d | awk '{print $1}' | sed 's/\\.$//g'
> drwxr-x---
$ getfacl --omit-header d
> user::rwx
> group::r-x
> other::---
>
Now, chmod should change the group_obj entry
$ chmod 775 d
$ ls -dl d | awk '{print $1}' | sed 's/\\.$//g'
> drwxrwxr-x
$ getfacl --omit-header d
> user::rwx
> group::rwx
> other::r-x
>
$ rmdir d
$ umask 002
$ mkdir d
$ setfacl -m u:daemon:rwx,u:bin:rx,d:u:daemon:rwx,d:u:bin:rx d
$ ls -dl d | awk '{print $1}'
> drwxrwxr-x+
$ getfacl --omit-header d
> user::rwx
> user:bin:r-x
> user:daemon:rwx
> group::rwx
> mask::rwx
> other::r-x
> default:user::rwx
> default:user:bin:r-x
> default:user:daemon:rwx
> default:group::rwx
> default:mask::rwx
> default:other::r-x
>
$ chmod 750 d
$ ls -dl d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d
> user::rwx
> user:bin:r-x
> user:daemon:rwx #effective:r-x
> group::rwx #effective:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:r-x
> default:user:daemon:rwx
> default:group::rwx
> default:mask::rwx
> default:other::r-x
>
$ chmod 750 d
$ ls -dl d | awk '{print $1}'
> drwxr-x---+
$ getfacl --omit-header d
> user::rwx
> user:bin:r-x
> user:daemon:rwx #effective:r-x
> group::rwx #effective:r-x
> mask::r-x
> other::---
> default:user::rwx
> default:user:bin:r-x
> default:user:daemon:rwx
> default:group::rwx
> default:mask::rwx
> default:other::r-x
>
$ rmdir d
Dangling symlink test http://savannah.nongnu.org/bugs/?28131
$ mkdir d
$ ln -s d/a d/b
$ getfacl -R d
> # file: d
> # owner: %TUSER
> # group: %TGROUP
> user::rwx
> group::rwx
> other::r-x
>
$ setfacl -R -m u:bin:rw d
$ getfacl -RL d
> getfacl: d/b: No such file or directory
> # file: d
> # owner: %TUSER
> # group: %TGROUP
> user::rwx
> user:bin:rw-
> group::rwx
> mask::rwx
> other::r-x
>
$ setfacl -RL -m u:bin:rw d
> setfacl: d/b: No such file or directory
$ rm -R d
Handle escaped literal backslash followed by numeric username
$ mkdir d
$ touch d/f
$ setfacl -m u:domain\\\\12345:rw- d/f
$ getfacl --omit-header d/f
> user::rw-
> user:domain\\12345:rw-
> group::rw-
> mask::rw-
> other::r--
>
$ rm -R d
Handle escaped literal backslash
$ mkdir d
$ touch d/f
$ setfacl -m u:domain\\\\user:rw- d/f
$ getfacl --omit-header d/f
> user::rw-
> user:domain\\user:rw-
> group::rw-
> mask::rw-
> other::r--
>
$ rm -R d
Handle escaped literal characters by octal code (bin)
$ mkdir d
$ touch d/f
$ setfacl -m u:\\142\\151\\156:rw- d/f
$ getfacl --omit-header d/f
> user::rw-
> user:bin:rw-
> group::rw-
> mask::rw-
> other::r--
>
$ rm -R d
Malformed restore file
$ echo "# owner: root" > f
$ setfacl --restore=f 2>&1
>setfacl: f: No filename found in line 0, aborting