OCI runtime create failed: executable file not found in $PATH
Fix "executable file not found in $PATH": run docker run --rm -it --entrypoint sh image, then fix the COPY path, exec-form CMD or missing shell.
OCI runtime create failed: container_linux.go:380: starting container process caused: exec: "myapp": executable file not
Incident Overview
Fix "executable file not found in $PATH": run docker run --rm -it --entrypoint sh image, then fix the COPY path, exec-form CMD or missing shell.
easy fix·7 min read·4 causes
By Vishvesh Patel·DevOps Engineer·Updated 21 September 2026
OCI runtime create failed: container_linux.go:380: starting container process caused: exec: "myapp": executable file not found in $PATH: unknown docker: Error response from daemon: failed to create task for container: failed to create shim task: OCI runtime create failed: exec: "/app/start.sh": stat /app/start.sh: no such file or directory: unknown exec: "bash": executable file not found in $PATH
Do this first3 steps
Run these in order. Each one tells you what its output means before you change anything.
• Look inside the image without running the failing command
Overriding the entrypoint lets you inspect an image whose normal start command is broken. If ls shows nothing at the expected path, the COPY never landed where you think it did.
• Check the binary is executable and is the right architecture
A file without the x bit gives permission denied rather than not found, and a binary built for another architecture gives exec format error. Both are commonly mistaken for this error.
• Inspect what the image is actually configured to run
Compare this against what exists in the image. The runtime concatenates ENTRYPOINT and CMD, so an unexpected combination here explains most of these failures.
docker run --rm -it --entrypoint sh myapp:1.0 -c 'ls -l /app && echo "PATH=$PATH"'
Then: the 4 causes in full
If the steps above did not settle it, these are the causes in the order they are usually responsible. Each section explains why it happens and how to confirm it.
executable file not found in $PATH means the container was created successfully and then the runtime could not find the program it was told to start. The image is fine. The start command is wrong, or the file it names is not where the runtime is looking.
Note that this is a different failure from exec format error, which means the file was found and the kernel could not run it. Found-but-unrunnable is an architecture problem; not-found is this page.
Look inside the image
You cannot docker run your way in when the entrypoint is what is broken, so override it:
Then check the two things that matter:
If the binary is not in /app, or /app is empty, the COPY in your Dockerfile did not put it where you think. That is the most common root cause and it is invisible until you look.
If the image has no shell either, see the distroless section below.
docker run --rm -it --entrypoint sh myapp:1.0
Check what the image is configured to run
The runtime runs ENTRYPOINT followed by CMD. Getting this combination wrong produces surprising results: with an ENTRYPOINT set, a command you pass to docker run replaces CMD and becomes an argument to the entrypoint, not a new command. That is why
on an image with ENTRYPOINT ["/app/server"] tries to run /app/server bash rather than giving you a shell.
docker image inspect myapp:1.0 \
--format 'ENTRYPOINT={{.Config.Entrypoint}} CMD={{.Config.Cmd}}'Cause 1: The COPY destination is not what you assumed
Looks right, and the trailing . is the trap. COPY src . copies into the working directory when the source is a file, so this produces /app/server and works. But:
copies the contents of build/ into /app, whereas
copies the directory itself, producing /app/build/server. One character of difference, and CMD ["/app/server"] then points at nothing.
Be explicit and verify:
That RUN test -x fails the build rather than shipping an image that cannot start, which is a much cheaper place to find out.
WORKDIR /app COPY build/server . CMD ["./server"]
Cause 2: Exec form cannot use the shell
Exec form passes the string straight to execve. There is no shell, which means no $VAR expansion, no &&, no globbing, no PATH search of a relative path. These all fail in exec form:
The last is worth dwelling on: CMD ["node server.js"] looks for a program literally named node server.js, space included. Exec form takes one array element per argument:
If you genuinely need shell features, be explicit about it:
The exec matters. Without it the shell stays as PID 1 and does not forward SIGTERM, so your container ignores docker stop and gets killed after the timeout. That shows up later as slow deploys and dropped connections, and it is easy to miss.
CMD ["./start.sh"] # exec form: no shell involved CMD ./start.sh # shell form: runs via /bin/sh -c
Cause 3: The shell or tool is not in the image
Alpine has no bash. It ships BusyBox ash as /bin/sh.
Use sh, or install bash if you need it:
The same applies to curl, wget, ps and most of what you assume is present. BusyBox provides cut-down versions of some of these and not others, and the cut-down ones do not always accept the flags you expect.
FROM alpine:3.20 CMD ["bash", "-c", "echo hi"] # exec: "bash": executable file not found
Cause 4: Distroless and scratch images
gcr.io/distroless/* and scratch contain no shell at all. That is the point: less to exploit. It also means:
Only exec form works, naming the binary directly:
To inspect one, use the :debug variant, which includes BusyBox:
Or look at the filesystem from outside without running anything:
docker export works on a created-but-never-started container, so it works even when the image cannot start at all. It is the most reliable way to answer "what is actually in this image".
FROM gcr.io/distroless/static-debian12 COPY --from=build /out/server /server ENTRYPOINT ["/server"]
The two errors people confuse with this one
For the middle one:
--chmod on COPY avoids a separate RUN chmod layer, and it survives checkouts on Windows where the source file may arrive without the bit set.
COPY --chmod=0755 entrypoint.sh /entrypoint.sh
A checklist
Frequently Asked Questions
What does "executable file not found in $PATH" mean in Docker?
The container was created and the runtime then could not find the program it was told to execute. Either the file is not at the path given, or the name was given without a path and is not on PATH. It is specifically not an image-pull or permissions problem, and it is distinct from exec format error, which means the file was found and the kernel could not run it. Inspect the image with docker run --entrypoint sh and list the directory you expect the binary to be in.
Why does CMD ["node server.js"] fail?
Because exec form takes one array element per argument, so that asks for a program literally named node server.js, space included. Write CMD ["node", "server.js"]. The same mistake produces confusing results whenever people write a whole command line as a single string in exec form. Shell form, CMD node server.js, does work because it runs through /bin/sh -c, but then the shell becomes PID 1 and will not forward SIGTERM to your process unless you use exec.
Why can I not use bash in an Alpine image?
Alpine does not ship bash. It provides BusyBox ash as /bin/sh, which covers POSIX shell but not bash extensions such as arrays or [[ ]]. Any CMD ["bash", ...], RUN bash ... or docker exec ... bash fails with exactly this error. Either write POSIX-compatible shell and use sh, or add RUN apk add --no-cache bash. The same applies to tools you may assume are present, such as curl, since Alpine's BusyBox provides only a subset and sometimes with different flags.
How do I debug an image with no shell, like distroless?
Two options. Use the :debug tag of the distroless image, which includes BusyBox, so --entrypoint sh works. Or inspect the filesystem from outside without running anything: docker create --name tmp <image> then docker export tmp | tar -tv. The second works even when the image cannot start at all, because docker create never executes the entrypoint, which makes it the most dependable way to answer what is actually inside a broken image.
What is the difference between "executable file not found" and "permission denied"?
Not found means the path does not resolve to a file at all, usually a wrong COPY destination or a name that is not on PATH. Permission denied means the file exists but does not have the executable bit set, which happens frequently with scripts checked out on Windows or copied from an archive that did not preserve the mode. Fix the second with COPY --chmod=0755 script.sh /script.sh, which avoids an extra RUN chmod layer and does not depend on the mode of the file on the build machine.
Reference and practice
Learn the underlying concept
Other Docker errors
Free, comprehensive DevOps tutorials and learning roadmaps. Master Docker, Kubernetes, CI/CD, and more.
Get notified about new tutorials and features.
• Roadmaps
• Interview Prep
• Certifications
• Company
© 2026 DevOpsLesson. All rights reserved.
Need to practice this scenario?
Simulate this error condition and practice recovery commands safely in our in-browser terminal.