Eliminar CRLF

Para mantener el estándar usado en los antiguos Teletipos,
DOS/Windows utiliza dos caracteres de control para representar un salto de línea: un
Carriage Return (CR = 0x0D) y un
Line Feed (LF = 0x0A). Los sistemas tipo Unix se dieron
cuenta de que eso desperdicia 1 byte por línea y que basta con un LF para representar una nueva
línea.
Ejemplo:
$ cat bacon.txt
Bacon Ipsum:
Bacon ipsum dolor sit amet salami
pork belly tail tongue pancetta,
pork loin tri-tip drumstick bresaola shankle.
$ file bacon_windows.txt bacon_linux.txt
bacon_windows.txt: ASCII text, with CRLF line terminators
bacon_linux.txt: ASCII text
$ hexdump -C bacon_linux.txt
00000000 42 61 63 6f 6e 20 49 70 73 75 6d 3a <strong>0a 0a</strong> 42 61 |Bacon Ipsum:..Ba|
00000010 63 6f 6e 20 69 70 73 75 6d 20 64 6f 6c 6f 72 20 |con ipsum dolor |
00000020 73 69 74 20 61 6d 65 74 20 73 61 6c 61 6d 69 <strong>0a</strong> |sit amet salami.|
00000030 70 6f 72 6b 20 62 65 6c 6c 79 20 74 61 69 6c 20 |pork belly tail |
00000040 74 6f 6e 67 75 65 20 70 61 6e 63 65 74 74 61 2c |tongue pancetta,|
00000050 <strong>0a</strong> 70 6f 72 6b 20 6c 6f 69 6e 20 74 72 69 2d 74 |.pork loin tri-t|
00000060 69 70 20 64 72 75 6d 73 74 69 63 6b 20 62 72 65 |ip drumstick bre|
00000070 73 61 6f 6c 61 20 73 68 61 6e 6b 6c 65 2e <strong>0a</strong> |saola shankle..|
0000007f
$ hexdump -C bacon_windows.txt
00000000 42 61 63 6f 6e 20 49 70 73 75 6d 3a <strong>0d 0a 0d 0a</strong> |Bacon Ipsum:....|
00000010 42 61 63 6f 6e 20 69 70 73 75 6d 20 64 6f 6c 6f |Bacon ipsum dolo|
00000020 72 20 73 69 74 20 61 6d 65 74 20 73 61 6c 61 6d |r sit amet salam|
00000030 69 <strong>0d 0a</strong> 70 6f 72 6b 20 62 65 6c 6c 79 20 74 61 |i..pork belly ta|
00000040 69 6c 20 74 6f 6e 67 75 65 20 70 61 6e 63 65 74 |il tongue pancet|
00000050 74 61 2c <strong>0d 0a</strong> 70 6f 72 6b 20 6c 6f 69 6e 20 74 |ta,..pork loin t|
00000060 72 69 2d 74 69 70 20 64 72 75 6d 73 74 69 63 6b |ri-tip drumstick|
00000070 20 62 72 65 73 61 6f 6c 61 20 73 68 61 6e 6b 6c | bresaola shankl|
00000080 65 2e <strong>0d 0a</strong> |e...|
00000084
Observa que el archivo creado en Windows contiene la secuencia 0d 0a donde el creado en Linux
tiene solo 0a. Esto trae problemas de compatibilidad y dolores de cabeza.
Aunque buenos editores consiguen trabajar con ambos (en Notepad las líneas de bacon_linux.txt
aparecerán concatenadas), archivos que supuestamente deberían ser iguales aparecen como diferentes
si usamos herramientas como “diff”:
$ diff bacon_windows.txt bacon_linux.txt
1,5c1,5
< Bacon Ipsum:
<
< Bacon ipsum dolor sit amet salami
< pork belly tail tongue pancetta,
< pork loin tri-tip drumstick bresaola shankle.
---
> Bacon Ipsum:
>
> Bacon ipsum dolor sit amet salami
> pork belly tail tongue pancetta,
> pork loin tri-tip drumstick bresaola shankle.
Hoy puse en control de versiones algunos códigos hechos en parte en Windows y parte en Linux y preferí estandarizar todo a LF. Aquí muestro cómo hice la conversión automáticamente en Linux:
Vim
Dos formas:
1
- Mostrar
CRLFcomo^M::e ++ff=unix. - Sustituir todos los
^Mpor^N::s/\r/\r/. - Quitar
^Msolo si está al final de la línea::s/\r\+$// - Quitar todos los
^M::s/^M//
^M se teclea como ^V^M (ctrl+V ctrl+M).
2
- Convertir el formato del archivo a unix:
:setlocal fileformat=unix - Guardar:
:w - Recargar:
:e
Convertir varios archivos
- Asume formato DOS:
:set ffs=dos. - Lista de archivos a convertir:
:args *.c *.h. - Cambia el formato de cada argumento:
:argdo set ff=unix|w.
Otros comandos útiles: :set list y :set nobomb.
sed
sed, Stream EDitor, es uno de los utilitarios de línea para procesar texto más útiles.
Trabaja línea a línea, así que si sabemos que el archivo está en formato DOS podemos usar sed para
sustituir los dos últimos caracteres (CRLF = /r/n) de cada línea por solo LF (/n):
sed -i 's/.$//' archivo.txt
Cuidado: si el archivo ya está en formato Unix, terminarás borrando el último carácter de cada línea.
La conversión contraria (a DOS) también puede hacerse con GNU sed:
sed -i 's/$/\r/' archivo.txt
Tofrodos
Si no quieres preocuparte en verificar si el archivo ya sigue el estándar Unix, una alternativa a
sed es Tofrodos. Si el archivo ya está convertido, lo deja tal cual; es especialmente útil en
scripts.
Descarga e instala Tofrodos, disponible en el AUR. (O
dos2unixdecommunity)Ejecuta el siguiente comando en la carpeta que irá al control de versiones (donde
^MesCtrl+V+Ctrl+M):grep -IUrl --color '^M' . | xargs -ifile fromdos 'file'
Este comando convertirá todos los CR+LF a LF en todos los archivos de la carpeta actual y
subcarpetas.
Cambia fromdos por todos para convertir en sentido contrario (LF a CR+LF).
Enlaces

Soy un ingeniero informático brasileño radicado en Alemania, apasionado por la tecnología, la ciencia, la fotografía y los idiomas.
Llevo programando cerca de dos décadas, explorando desde apps móviles y desarrollo web hasta aprendizaje automático. Hoy me enfoco en SRE en la nube e ingeniería de datos.
Soy voluntario en las comunidades de open source y Python, ayudando a organizar PyCon DE y PyData Berlin, dando mentorías y contribuyendo con código y traducciones.
En mi blog comparto consejos de Linux, guías de configuración y notas personales que escribí como referencia futura. Espero que también sean útiles para otras personas. El contenido está disponible en varios idiomas.
Visita mi galería para ver algunas de mis fotografías.
Fuera del teclado, me encontrarás en conciertos, tocando el clarinete, en bicicleta, buceando o explorando nuevos lugares, culturas y cocinas.
¡Siempre feliz de conectar! 🙂