1 <sect1 id="using-textbinary"><title>Text and Binary modes</title>
3 <sect2 id="textbin-issue"> <title>The Issue</title>
5 <para>On a UNIX system, when an application reads from a file it gets
6 exactly what's in the file on disk and the converse is true for writing.
7 The situation is different in the DOS/Windows world where a file can
8 be opened in one of two modes, binary or text. In the binary mode the
9 system behaves exactly as in UNIX. However on writing in text mode, a
10 NL (\n, ^J) is transformed into the sequence CR (\r, ^M) NL.
13 <para>This can wreak havoc with the seek/fseek calls since the number
14 of bytes actually in the file may differ from that seen by the
17 <para>The mode can be specified explicitly as explained in the Programming
18 section below. In an ideal DOS/Windows world, all programs using lines as
19 records (such as <command>bash</command>, <command>make</command>,
20 <command>sed</command> ...) would open files (and change the mode of their
21 standard input and output) as text. All other programs (such as
22 <command>cat</command>, <command>cmp</command>, <command>tr</command> ...)
23 would use binary mode. In practice with Cygwin, programs that deal
24 explicitly with object files specify binary mode (this is the case of
25 <command>od</command>, which is helpful to diagnose CR problems). Most
26 other programs (such as <command>cat</command>, <command>cmp</command>,
27 <command>tr</command>) use the default mode.</para>
31 <sect2 id="textbin-default"><title>The default Cygwin behavior</title>
33 <para>The Cygwin system gives us some flexibility in deciding how files
34 are to be opened when the mode is not specified explicitly.
35 The rules are evolving, this section gives the design goals.</para>
37 <orderedlist numeration="loweralpha">
39 <para>If the filename is specified as a POSIX path and it appears to
40 reside on a file system that is mounted (i.e. if its pathname starts
41 with a directory displayed by <command>mount</command>), then the
42 default is specified by the mount flag. If the file is a symbolic link,
43 the mode of the target file system applies.</para>
47 <para>If the file is specified via a MS-DOS pathname (i.e., it contains a
48 backslash or a colon), the default is binary.
53 <para>Pipes, sockets and non-file devices are opened in binary mode.
54 For pipes opened through the pipe() system call you can use the setmode()
55 function (see <xref linkend="textbin-devel"></xref> to switch to textmode.
56 For pipes opened through popen(), you can simply specify text or binary
57 mode just like in calls to fopen().</para>
61 <para>Sockets and other non-file devices are always opened in binary mode.
66 <para> When redirecting, the Cygwin shells uses rules (a-d).
67 Non-Cygwin shells always pipe and redirect with binary mode. With
68 non-Cygwin shells the commands <command> cat filename | program </command>
69 and <command> program < filename </command> are not equivalent when
70 <filename>filename</filename> is on a text-mounted partition. </para>
75 <sect2 id="textbin-example"><title>Example</title>
76 <para>To illustrate the various rules, we provide scripts to delete CRs
77 from files by using the <command>tr</command> program, which can only write
83 # Remove \r from the file given as argument
84 tr -d '\r' < "$1" > "$1".nocr
87 <para> will not work on a text mounted systems because the \r will be
88 reintroduced on writing. However scripts such as </para>
92 # Remove \r from the file given as argument
93 tr -d '\r' | gzip | gunzip > "$1".nocr
96 <para>and the .bat file</para>
99 REM Remove \r from the file given as argument
101 tr -d \r < %1 > %1.nocr
104 <para> work fine. In the first case we rely on <command>gunzip</command> to
105 set its output to binary mode, possibly overriding the mode used by the shell.
106 In the second case we rely on the DOS shell to redirect in binary mode.
110 <sect2 id="textbin-question"><title>Binary or text?</title>
112 <para>UNIX programs that have been written for maximum portability
113 will know the difference between text and binary files and act
114 appropriately under Cygwin. Most programs included in the official
115 Cygwin distributions should work well in the default mode. </para>
117 <para>Binmode is the best choice usually since it's faster and
118 easier to handle, unless you want to exchange files with native Win32
119 applications. It makes most sense to keep the Cygwin distribution
120 and your Cygwin home directory in binmode and generate text files in
121 binmode (with UNIX LF lineendings). Most Windows applications can
122 handle binmode files just fine. A notable exception is the mini-editor
123 <command>Notepad</command>, which handles UNIX lineendings incorrectly
124 and only produces output files with DOS CRLF lineendings.</para>
126 <para>You can convert files between CRLF and LF lineendings by using
127 certain tools in the Cygwin distribution like <command>d2u</command> and
128 <command>u2d</command> from the cygutils package. You can also specify
129 a directory in the mount table to be mounted in textmode so you can use
130 that directory for exchange purposes.</para>
132 <para>As application programmer you can decide on a file by file base,
133 or you can specify default open modes depending on the purpose for which
134 the application open files. See the next section for a description of
139 <sect2 id="textbin-devel"><title>Programming</title>
141 <para>In the <function>open()</function> function call, binary mode can be
142 specified with the flag <literal>O_BINARY</literal> and text mode with
143 <literal>O_TEXT</literal>. These symbols are defined in
144 <filename>fcntl.h</filename>.</para>
146 <para>In the <function>fopen()</function> and <function>popen()</function>
147 function calls, binary mode can be specified by adding a <literal>b</literal>
148 to the mode string. Text mode is specified by adding a <literal>t</literal>
149 to the mode string.</para>
151 <para>The mode of a file can be changed by the call
152 <function>setmode(fd,mode)</function> where <literal>fd</literal> is a file
153 descriptor (an integer) and <literal>mode</literal> is
154 <literal>O_BINARY</literal> or <literal>O_TEXT</literal>. The function
155 returns <literal>O_BINARY</literal> or <literal>O_TEXT</literal> depending
156 on the mode before the call, and <literal>EOF</literal> on error.</para>
158 <para>There's also a convenient way to set the default open modes used
159 in an application by just linking against various object files provided
160 by Cygwin. For instance, if you want to make sure that all files are
161 always opened in binary mode by an application, regardless of the mode
162 of the underlying mount point, just add the file
163 <filename>/lib/binmode.o</filename> to the link stage of the application
164 in your project, like this:</para>
167 $ gcc my_tiny_app.c /lib/binmode.o -o my_tiny_app
170 <para>This adds code which sets the default open mode for all files
171 opened by <command>my_tiny_app</command> to binary for reading and
174 <para>Cygwin provides the following object files to set the default open mode
175 just by linking an application against them:</para>
177 <itemizedlist mark="bullet">
181 /lib/automode.o - Open files for reading in textmode
182 Open files for writing in binary mode
188 /lib/binmode.o - Open files for reading and writing in binary mode
194 /lib/textmode.o - Open files for reading and writing in textmode
200 /lib/textreadmode.o - Open files for reading in textmode
201 Keep default behaviour for writing.