Search code examples
linuxgitline-endings

Why does Git convert CRLF to LF on Linux?


I have some shell scripts that need to have LF line endings (I'm on Ubuntu 14.04). Since this is a cross-platform open source project, a .gitattributes file is used to make line endings work 'automatically'. Unfortunately, they don't.

$ cat .gitattributes
# automatically normalize line endings
* text=auto

I have the following file on my file system:

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

If I now process it using dos2unix, it shows correctly as LF terminated.

$ file extract.sh 
extract.sh: Bourne-Again shell script, ASCII text executable

Also, git shows it as modified:

$ git status
[..]
Changes not staged for commit:
[..]

    modified:   extract.sh

Now I add it to the index:

$ git add extract.sh 
warning: LF will be replaced by CRLF in extract.sh.
The file will have its original line endings in your working directory.

But a new git status shows this:

$ git status .
[..]

nothing to commit, working directory clean

And file shows it as unchanged:

$ file extract.sh 
extract.sh: Bourne-Again shell script, ASCII text executable

However, if I remove it and check it out again:

$ rm extract.sh 
$ git checkout extract.sh
$ file extract.sh 
extract.sh: Bourne-Again shell script, ASCII text executable, with CRLF line terminators
$ git status .
[..]

nothing to commit, working directory clean

Even removing it from the cache doesn't help:

$ git rm --cached extract.sh
$ git reset --hard
$ file extract.sh 
extract.sh: Bourne-Again shell script, ASCII text executable, with CRLF line terminators

The $100 question is: how do I get git to give me an LF terminated file?


Solution

  • From http://git-scm.com/book/en/Customizing-Git-Git-Configuration

    If you’re on a Linux or Mac system that uses LF line endings, then you don’t want Git to automatically convert them when you check out files; however, if a file with CRLF endings accidentally gets introduced, then you may want Git to fix it. You can tell Git to convert CRLF to LF on commit but not the other way around by setting core.autocrlf to input:

    git config --global core.autocrlf input