A Linux ACL (access control list) is a set of additional permission entries attached to a file or directory that grants read, write and execute rights to specific named users and groups beyond the classic owner, group and other classes. In Linux permissions, ACLs follow the POSIX.1e draft model and are managed with the getfacl and setfacl commands.
Standard Unix permissions allow exactly one owning user and one owning group per file. ACLs remove that limit, so a project directory can be writable by one team, readable by another and accessible to a single auditor, without creating artificial groups or loosening permissions for everyone.
How Linux ACLs extend standard permissions
An ACL is stored as an extended attribute of the inode, named system.posix_acl_access for files and additionally system.posix_acl_default for directory defaults. The kernel evaluates it during every permission check, so it applies to all programs, not only to particular tools.
A file without extra entries has a minimal ACL that is equivalent to its mode bits. As soon as a named user or group is added, the file has an extended ACL, and ls -l shows a plus sign after the permission string, for example -rw-rw-r--+.
The entry types are listed below, with the notation used by getfacl.
| Entry | Notation | Meaning |
|---|---|---|
| Owner | user::rw- | Rights of the file owner |
| Named user | user:anna:rw- | Rights of a specific additional user |
| Owning group | group::r-- | Rights of the file’s group |
| Named group | group:audit:r-- | Rights of a specific additional group |
| Mask | mask::rw- | Upper limit for named entries and the owning group |
| Other | other::--- | Rights of everyone else |
The access check algorithm and the mask
The kernel evaluates ACL entries in a fixed order and stops at the first matching class, rather than combining all entries.
- If the process owns the file, the owner entry applies.
- Otherwise, if a named user entry matches, it applies, limited by the mask.
- Otherwise, if any of the process groups matches the owning group or a named group, access is granted if one matching entry, limited by the mask, allows it.
- Otherwise, the other entry applies.
The mask entry is the most misunderstood element. It defines the maximum effective rights for named users, named groups and the owning group. When a file has an extended ACL, the group bits shown by ls -l and changed by chmod g= represent the mask, not the owning group. A chmod 640 can therefore silently remove write access granted to a named user, which getfacl reports with an #effective: comment.
Managing ACLs with getfacl and setfacl
ACLs are administered with two commands from the acl package. The table shows the operations used most often.
| Command | Effect | Note |
|---|---|---|
getfacl file | Displays all entries | Shows effective rights where the mask limits them |
setfacl -m u:anna:rw file | Adds or modifies an entry | Recalculates the mask by default |
setfacl -x g:audit file | Removes one entry | Other entries stay unchanged |
setfacl -b file | Removes all extended entries | Leaves only the mode bits |
setfacl -R -m ... dir | Applies recursively | Affects existing files only |
setfacl -d -m g:dev:rwx dir | Sets a default ACL | Inherited by new files and subdirectories |
getfacl -R dir > acl.txt and setfacl --restore=acl.txt | Backs up and restores ACLs | Useful before risky changes |
Default ACLs exist only on directories and act as a template. A new file inherits the default entries as its access ACL, while a new subdirectory inherits them both as access and default ACL. The requested mode of the creating program still applies and can narrow the result through the mask; when a default ACL exists, the umask is not used.
ACLs compared with other permission mechanisms
ACLs are one layer of Linux access control and work together with neighboring tools in the permissions topic.
| Mechanism | Granularity | Typical purpose |
|---|---|---|
| Mode bits via chmod and chown | Owner, one group, others | Simple ownership-based access |
| umask | Default bits for new files | Restricting permissions at creation |
| POSIX ACLs | Any number of named users and groups | Shared directories with mixed access |
| NFSv4 ACLs | Allow and deny entries with fine rights | Network shares, closer to Windows semantics |
| SELinux or AppArmor | Policy per process and label | Mandatory confinement of services |
| sudo | Commands per user | Controlled privilege elevation |
POSIX ACLs are discretionary: the file owner can change them. They cannot restrict the root account, which bypasses discretionary checks; for that, mandatory access control such as SELinux is required.
Support, pitfalls and good practice
Modern filesystems such as ext4, XFS and Btrfs support ACLs and enable them by default. Problems usually appear when files leave the original filesystem or when tools ignore extended attributes.
- Lost ACLs when copying: plain
cpdrops them; usecp -a,rsync -Aortar --acls. - chmod overriding access: changing group bits modifies the mask and can reduce named entries.
- Recursive changes without defaults:
setfacl -Rfixes existing files but new files need a default ACL. - Execute bit on files:
rwXwith a capital X grants execute only to directories and already executable files. - Too many individual users: long per-user lists are hard to audit; named groups scale better.
A maintainable approach is to grant ACL entries to groups rather than individuals, set default ACLs on shared directories when they are created, and include ACL listings in regular permission audits.
In simple terms
Ordinary Linux permissions work like a door with three keys: one for the owner, one for a single group and one for everybody else. That is often too coarse when several teams need different kinds of access to the same folder.
An ACL is a guest list attached to the door. It names extra people or groups and says exactly what each may do, such as only reading or also editing. The result is precise sharing without opening the door to everyone.
A practical example
A company keeps project files in /srv/projects/alpha on a Linux file server. The developers’ group must read and write, the quality team must only read, and an external auditor account needs read access for one quarter. With mode bits alone, only one group can be the owning group, so the requirement cannot be met cleanly.
The administrator sets the developers as the owning group, then runs setfacl -m g:qa:rX,u:auditor:rX recursively and adds matching default ACL entries so that new files inherit the same rules. Backups are switched to rsync -A so the entries survive restores.
Every team gets exactly the access it needs, and removing the auditor later takes a single recursive setfacl -x command, with no change to anyone else’s permissions.