Running the container with seccomp option doesn't work anymore
Describe the bug
The container fails to start when using the seccomp option. I'm simply following the https://github.com/jlandure/alpine-chrome?tab=readme-ov-file#-the-best-with-seccomp section. This used to work fine for me one or two weeks ago.
To Reproduce Steps to reproduce the behavior:
- Image version:
zenika/alpine-chrome@sha256:dbbe4612e677d952996ce1281ada255f58c5b6f8115f02e0dc075f2742a3de2b - Download chrome.json
wget https://raw.githubusercontent.com/jfrazelle/dotfiles/master/etc/docker/seccomp/chrome.json - Start the container
docker container run -it --rm --security-opt seccomp=$(pwd)/chrome.json zenika/alpine-chrome
What is the expected behavior?
The container starts.
What is the actual behavior?
The container fails to start with this error:
docker: Error response from daemon: failed to create task for container: failed to create shim task: OCI runtime create failed: runc create failed: unable to start container process: error during container init: error closing exec fds: get handle to /proc/thread-self/fd: unsafe procfs detected: openat2 fsmount:fscontext:proc/thread-self/fd/: function not implemented: unknown
Possible solution
No idea.
Logs
I don't have other logs.
Versions
| Software | Version(s) | How-to |
|---|---|---|
| Chromium | 124.0.6367.78 | docker container run -it --rm --entrypoint "" zenika/alpine-chrome chromium-browser --version |
| Image | dbbe4612e677d952996ce1281ada255f58c5b6f8115f02e0dc075f2742a3de2b | docker image inspect --format='{{index .RepoDigests 0}}' zenika/alpine-chrome |
| Docker Engine | 28.5.2 | docker version |
Additional context
$ docker version
Client: Docker Engine - Community
Version: 28.5.2
API version: 1.51
Go version: go1.25.3
Git commit: ecc6942
Built: Wed Nov 5 14:43:22 2025
OS/Arch: linux/amd64
Context: default
Server: Docker Engine - Community
Engine:
Version: 28.5.2
API version: 1.51 (minimum version 1.24)
Go version: go1.25.3
Git commit: 89c5e8f
Built: Wed Nov 5 14:43:22 2025
OS/Arch: linux/amd64
Experimental: false
containerd:
Version: v1.7.29
GitCommit: 442cb34bda9a6a0fed82a2ca7cade05c5c749582
runc:
Version: 1.3.3
GitCommit: v1.3.3-0-gd842d771
docker-init:
Version: 0.19.0
GitCommit: de40ad0
I upgraded a few days ago to Ubuntu 25.10:
$ uname -a
Linux yoga 6.17.0-6-generic #6-Ubuntu SMP PREEMPT_DYNAMIC Tue Oct 7 13:34:17 UTC 2025 x86_64 GNU/Linux
but it was failing on Ubuntu 25.04 before the upgrade. It used to work on Ubuntu 25.04 one or two weeks ago. I'm not sure what changed...
I asked Copilot to analyze the issue and I got this response (pasting only relevant parts):
The issue is that the newer Chrome version (124) in the
zenika/alpine-chrome:124Docker image is trying to use theopenat2system call, which is not included in your current seccomp profile (chrome.json).The error message specifically mentions:
openat2 fsmount:fscontext:proc/thread-self/fd/ function not implementedThis indicates that the
openat2system call is being blocked by the seccomp profile.Why this happened:
- Chrome evolution: Chrome 124 introduced new security features that require additional system calls, particularly around the newer filesystem APIs (openat2, fsmount, etc.)
- System call additions: The openat2 system call was added to Linux kernel 5.6 (March 2020) and provides enhanced functionality over the traditional open/openat calls
- Container security: Modern Chrome versions are increasingly using newer kernel features for enhanced security and performance
Additional system calls you might need: The system calls I added (
openat2,fsopen,fsconfig,fsmount,move_mount,fspick) are part of the newer Linux filesystem API that Chrome might use for:
- Enhanced file access controls
- Mount namespace operations
- Improved security isolation
The suggested addition was:
{
"name": "openat2",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "fsopen",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "fsconfig",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "fsmount",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "move_mount",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "fspick",
"action": "SCMP_ACT_ALLOW",
"args": null
},
With this I got a different error:
docker: Error response from daemon: failed to create task for container: failed to create shim task: OCI runtime create failed: runc create failed: unable to start container process: error during container init: error closing exec fds: get handle to /proc/thread-self/fd: reopen fsmount:fscontext:proc/thread-self/fd/: check safety of /proc/thread-self/fd/3 magiclink: get root mount id: statx(STATX_MNT_ID_...) fsmount:fscontext:proc/: could not get mount id: operation not permitted: unknown
The analysis for this was:
The error shows that Chrome is now trying to use even more advanced system calls. The new error mentions
statxwithSTATX_MNT_IDwhich is a newer variant of thestatfamily of system calls that provides extended file metadata including mount IDs.System calls I added and why:
statx- This is the key one causing your current error. It's an extended version of stat that can provide mount IDs and other advanced filesystem metadata. Chrome 124 is using this with the STATX_MNT_ID flag to get mount information.pidfd_open,pidfd_send_signal,pidfd_getfd- These are newer process file descriptor APIs that modern Chrome versions use for better process management and security.close_range- A more efficient way to close multiple file descriptors at once, which Chrome might use during process cleanup.epoll_pwait2- An enhanced version of epoll_pwait with better timeout handling.
The suggested addition was:
{
"name": "statx",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "pidfd_open",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "pidfd_send_signal",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "pidfd_getfd",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "close_range",
"action": "SCMP_ACT_ALLOW",
"args": null
},
{
"name": "epoll_pwait2",
"action": "SCMP_ACT_ALLOW",
"args": null
}
With this last change I managed to start the container with the seccomp option and all my automated tests are passing again. Here's the final diff:
@@ -1530,6 +1530,66 @@
"name": "writev",
"action": "SCMP_ACT_ALLOW",
"args": null
+ },
+ {
+ "name": "openat2",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "fsopen",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "fsconfig",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "fsmount",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "move_mount",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "fspick",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "statx",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "pidfd_open",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "pidfd_send_signal",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "pidfd_getfd",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "close_range",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
+ },
+ {
+ "name": "epoll_pwait2",
+ "action": "SCMP_ACT_ALLOW",
+ "args": null
}
]
}
I know very little about Linux system calls, so I would appreciate it if others review the change and tell me if there is something unsafe there. Thanks!
This repo here seems dead. The last published image in the GHCR registry was Chrome 124 more than a year ago.
And now a new image shows up in the Docker Registry at https://hub.docker.com/layers/zenika/alpine-chrome/124/images/sha256-2911036299faade5a651adb4f54e989121022702b38307c25072f0600ed7d3db, and it requires changes to the seccomp profile?
What is going on here?
@mpdude No support was given and I am no longer part of the company Zenika. Don't know what container is pushed now in the repo. DockerHub cannot move Repo from organization to another organization so it's complicated. From my side, I have no support and no access to Zenika DockerHub. Feel free to send an email to the Zenika DockerHub org to know what is the newly pushed content.
I just pushed new info on the README. Please see https://github.com/jlandure/alpine-chrome/blob/master/README.md
@jlandure 👌🏻. Thank you for the information, notice, response and the work you put into this in the past!
For me, it means I'll treat this newly pushed image as having unclear origins and not rely on it.