Trying to fix line-endings with git filter-branch, but having no luck

Viewed 76210

I have been bitten by the Windows/Linux line-ending issue with git. It seems, via GitHub, MSysGit, and other sources, that the best solution is to have your local repos set to use linux-style line endings, but set core.autocrlf to true. Unfortunately, I didn't do this early enough, so now every time I pull changes the line endings are borked.

I thought I had found an answer here but I can't get it to work for me. My Linux command line knowledge is limited at best, so i am not even sure what the "xargs fromdos" line does in his script. I keep getting messages about no such file or directory existing, and when I manage to point it to an existing directory, it tells me I don't have permissions.

I've tried this with MSysGit on Windows and via the Mac OS X terminal.

9 Answers

The git documentation for gitattributes now documents another approach for "fixing" or normalizing all the line endings in your project. Here's the gist of it:

$ echo "* text=auto" >.gitattributes
$ git add --renormalize .
$ git status        # Show files that will be normalized
$ git commit -m "Introduce end-of-line normalization"

If any files that should not be normalized show up in git status, unset their text attribute before running git add -u.

manual.pdf -text

Conversely, text files that git does not detect can have normalization enabled manually.

weirdchars.txt text

This leverages a new --renormalize flag added in git v2.16.0, released Jan 2018. For older versions of git, there are a few more steps:

$ echo "* text=auto" >>.gitattributes
$ rm .git/index     # Remove the index to force git to
$ git reset         # re-scan the working directory
$ git status        # Show files that will be normalized
$ git add -u
$ git add .gitattributes
$ git commit -m "Introduce end-of-line normalization"
git status --short|grep "^ *M"|awk '{print $2}'|xargs fromdos

Explanation:

  • git status --short

    This displays each line that git is and is not aware of. Files that are not under git control are marked at the beginning of the line with a '?'. Files that are modified are marked with an M.

  • grep "^ *M"

    This filters out only those files that have been modified.

  • awk '{print $2}'

    This shows only the filename without any markers.

  • xargs fromdos

    This takes the filenames from the previous command and runs them through the utility 'fromdos' to convert the line-endings.

I had the same problem in one of my repos. If you are using both windows and linux systems for the same code repo and pulling and pushing simultaneously, try this:

First, set your git config as follows for windows:

git config --global core.autocrlf true

This will make sure to convert CRLF to LF when writing into the object database and then again replace LF with CRLF when writing out into the working directory. As a result, your repo will be safe with only one type of line endings and locally you'll have windows line ending on the windows system.

For linux/MAC set the git config as follows:

git config --global core.autocrlf input

This will make sure to convert CRLF to LF when writing into the object database but will not do the reverse, preserving LF which is needed for linux/MAC.

For the wrong line endings that are already there on your linux/MAC use dos2unix

For MAC:

brew install dos2unix # Installs dos2unix Mac
find . -type f -exec dos2unix {} \; # recursively removes windows related stuff

For Linux:

sudo apt-get install -y dos2unix # Installs dos2unix Linux
sudo find . -type f -exec dos2unix {} \; # recursively removes windows related stuff

Hope this solves your problem.

Related