Skip to content
Commitpedia
Log in Join & edit

Fix: bad interpreter or command not found after a script is copied from Windows (CRLF)

A script edited on Windows carries invisible carriage returns, so Linux looks for /bin/bash^M. How to spot CRLF line endings, convert them with sed or dos2unix and stop git from reintroducing them.

Drafted with AI from official documentation. Scripts were run in a test environment and repository links verified. Awaiting a human check. Did it work for you? Last edited Outdated?

Edit history of Fix: bad interpreter or command not found after a script is copied from Windows (CRLF): 1 recorded edit
Edit history · 1 edit
Type
Article
Edits
1
Editors
1
First issued
15 Oct 2026
Last edit
15 Oct 2026
Reading
3 min

You run a script and get one of these:

bash: ./deploy.sh: /bin/bash^M: bad interpreter: No such file or directory
./deploy.sh: line 2: $'\r': command not found
./deploy.sh: line 7: syntax error near unexpected token `$'do\r''
: No such file or directory
: command not found

Windows ends lines with two characters, carriage return plus line feed (CRLF, \r\n). Linux and macOS use only line feed. The \r is invisible in most editors but bash treats it as part of the text, so the interpreter becomes /bin/bash\r, which does not exist, and every command gets a \r glued to its end.

Confirm that line endings are the problem

file deploy.sh
# deploy.sh: Bourne-Again shell script, ASCII text executable, with CRLF line terminators

cat -v deploy.sh | head -n 3
# #!/bin/bash^M            <- the ^M is the carriage return

head -c 40 deploy.sh | od -c
# look for \r before \n

Cause 1: the file was saved with CRLF

Convert it in place. Any one of these works; sed is always available, dos2unix is a small extra package.

# GNU sed (Linux)
sed -i 's/\r$//' deploy.sh

# BSD sed (macOS) needs an explicit backup suffix, empty is fine
sed -i '' 's/\r$//' deploy.sh

# Portable: write to a new file
tr -d '\r' < deploy.sh > deploy.unix.sh && mv deploy.unix.sh deploy.sh

# Or install dos2unix (apt install dos2unix / brew install dos2unix)
dos2unix deploy.sh

Then in your editor switch the file to LF. In VS Code the line-ending indicator is at the bottom right (click CRLF and choose LF); set "files.eol": "\n" in settings to make it the default. Notepad++ has Edit, EOL Conversion.

Cause 2: git converts endings on checkout

If every clone on Windows produces CRLF scripts, the repository needs a .gitattributes file so git normalizes shell scripts to LF regardless of the machine’s core.autocrlf setting.

# .gitattributes in the repository root
* text=auto
*.sh text eol=lf
*.bash text eol=lf
Dockerfile text eol=lf

# After adding it, renormalize once and commit
git add --renormalize .
git commit -m "Normalize line endings"

On your Windows machine, git config --global core.autocrlf input keeps LF in the repository while still letting you edit; true converts to CRLF on checkout, which is what causes the problem for scripts.

Cause 3: the file went through Windows tooling

Files pasted through some remote desktop clipboards, downloaded from SharePoint or OneDrive, or edited over an SMB share in Notepad can pick up CRLF even if they started as LF. Convert on arrival with dos2unix, or make the receiving step do it, for example a Makefile or CI job that runs sed -i 's/\r$//' *.sh before executing anything.

Check that it is fixed

file deploy.sh            # no more "with CRLF line terminators"
bash -n deploy.sh          # syntax check without running
./deploy.sh

When it is not CRLF

  • bad interpreter: No such file or directory without ^M: the path in the shebang does not exist. Alpine, NixOS and FreeBSD do not have /bin/bash. Use #!/usr/bin/env bash, or install bash.
  • bad interpreter: Permission denied: the file system is mounted noexec (common for /tmp, USB sticks and some network shares). Check with findmnt -T deploy.sh and run the script as bash deploy.sh or move it.
  • A UTF-8 byte order mark at the start of the file breaks the shebang too: head -c 3 deploy.sh | od -c shows 357 273 277. Remove it with sed -i '1s/^\xEF\xBB\xBF//' deploy.sh on GNU sed, or save the file as UTF-8 without BOM in your editor.
  • command not found with no stray characters is a PATH problem, covered in its own Fix article.

Official documentation

Did this work for you?

No votes yet. Be the first.

If it did not work, the report form below tells the editors what went wrong.

See also

  • 0049 Pipes and redirection: connecting commands A pipe sends one command's output into another command, and redirection sends output to a file. Together they let small tools build… Beginner · Explains an idea · Linux, macOS Article Basics · Text processing 15 Oct 2026
  • 0050 File permissions: chmod, chown and what 755 means Every file has an owner, a group and read/write/execute permissions for three kinds of users. chmod changes the permissions and chown changes… Beginner · Explains an idea · Linux, macOS Article Basics 15 Oct 2026
  • 0051 Environment variables and PATH Environment variables are named settings that every program inherits from the shell. PATH is the one that tells the shell where to… Beginner · Explains an idea · Linux, macOS Article Basics 15 Oct 2026
  • 0057 Shell cheat sheet: everyday commands A quick reference for moving around, managing files, viewing and searching text, checking processes and disk space in bash and zsh, with… Beginner · Cheat sheet · Linux, macOS Article Basics · Command-line tools 15 Oct 2026
  • 0058 Safe bash script template with set ‑euo pipefail and trap A starting point for bash scripts that stops on errors, rejects unset variables, cleans up temp files on exit and parses options.… Intermediate · Cheat sheet · Linux, macOS Script Shell scripting 15 Oct 2026
  • 0059 Incremental snapshot backups with rsync A bash script that copies a folder into dated snapshots with rsync, hard-links unchanged files to the previous snapshot to save space,… Advanced · Step by step · Linux, macOS Script Backups & syncing · Shell scripting 15 Oct 2026

History

Every saved edit is kept. The plot on the sleeve draws one line per edit. Open any edit to see exactly what changed.

  1. Dominik +3,789 chars

Report a problem

Something wrong, unsafe or copied? Tell the editors.
What is wrong?