standards.7: Add URLs for a couple of standards.
[dragonfly.git] / share / man / man7 / script.7
1 .\"     $OpenBSD: script.7,v 1.4 2007/05/31 19:19:58 jmc Exp $
2 .\"
3 .\"     $NetBSD: script.7,v 1.1 2005/05/07 02:20:34 perry Exp $
4 .\"     $DragonFly: src/share/man/man7/script.7,v 1.2 2007/12/22 19:07:00 swildner Exp $
5 .\"
6 .\" Copyright (c) 2005 The NetBSD Foundation, Inc.
7 .\" All rights reserved.
8 .\"
9 .\" This document was originally contributed to The NetBSD Foundation
10 .\" by Perry E. Metzger of Metzger, Dowdeswell & Co. LLC.
11 .\"
12 .\" Redistribution and use in source and binary forms, with or without
13 .\" modification, are permitted provided that the following conditions
14 .\" are met:
15 .\" 1. Redistributions of source code must retain the above copyright
16 .\"    notice, this list of conditions and the following disclaimer.
17 .\" 2. Redistributions in binary form must reproduce the above copyright
18 .\"    notice, this list of conditions and the following disclaimer in the
19 .\"    documentation and/or other materials provided with the distribution.
20 .\" 3. All advertising materials mentioning features or use of this software
21 .\"    must display the following acknowledgement:
22 .\"        This product includes software developed by the NetBSD
23 .\"        Foundation, Inc. and its contributors.
24 .\" 4. Neither the name of The NetBSD Foundation nor the names of its
25 .\"    contributors may be used to endorse or promote products derived
26 .\"    from this software without specific prior written permission.
27 .\"
28 .\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
29 .\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
30 .\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
31 .\" PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
32 .\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
33 .\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
34 .\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
35 .\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
36 .\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
37 .\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
38 .\" POSSIBILITY OF SUCH DAMAGE.
39 .\"
40 .Dd December 21, 2007
41 .Dt SCRIPT 7
42 .Os
43 .Sh NAME
44 .Nm script
45 .Nd interpreter script execution
46 .Sh DESCRIPTION
47 The system is capable of treating a text file containing commands
48 intended for an interpreter, such as
49 .Xr sh 1
50 or
51 .Xr awk 1 ,
52 as an executable program.
53 .Pp
54 An
55 .Dq interpreter script
56 is a file which has been set executable (see
57 .Xr chmod 2 )
58 and which has a first line of the form:
59 .Pp
60 .D1 Li #! Ar pathname Op Ar argument
61 .Pp
62 The
63 .Sq #!
64 must appear as the first two characters of the file.
65 A space between the
66 .Sq #!
67 and
68 .Ar pathname
69 is optional.
70 At most one
71 .Ar argument
72 may follow
73 .Ar pathname ,
74 and the length of the entire line is limited (see below).
75 .Pp
76 If such a file is executed (such as via the
77 .Xr execve 2
78 system call), the interpreter specified by the
79 .Ar pathname
80 is executed by the system.
81 (The
82 .Ar pathname
83 is executed without regard to the
84 .Ev PATH
85 variable, so in general
86 .Ar pathname
87 should be an absolute path.)
88 .Pp
89 The arguments passed to the interpreter will be as follows.
90 .Va argv[0]
91 will be the path to the interpreter itself, as specified on the first
92 line of the script.
93 If there is an
94 .Ar argument
95 following
96 .Ar pathname
97 on the first line of the script, it will be passed as
98 .Va argv[1] .
99 The subsequent elements of
100 .Va argv
101 will be the path to the interpreter script file itself (i.e. the
102 original
103 .Va argv[0] )
104 followed by any further arguments passed when
105 .Xr execve 2
106 was invoked to execute the script file.
107 .Pp
108 By convention, it is expected that an interpreter will open the script
109 file passed as an argument and process the commands within it.
110 Typical interpreters treat
111 .Sq #
112 as a comment character, and thus will ignore the initial line of the script
113 because it begins
114 .Sq #! ,
115 but there is no requirement for this per se.
116 .Pp
117 On
118 .Dx ,
119 the length of the
120 .Sq #!
121 line, excluding the
122 .Sq #!
123 itself, is limited to
124 .Dv PATH_MAX
125 (as defined in
126 .In limits.h ) .
127 Other operating systems impose different limits on the length of
128 the
129 .Sq #!
130 line (see below).
131 .Pp
132 Note that the interpreter may not itself be an interpreter script.
133 If
134 .Ar pathname
135 does not point to an executable binary, execution of the interpreter
136 script will fail.
137 .Ss Trampolines and Portable Scripts
138 Different operating systems often have interpreters located in
139 different locations, and the kernel executes the passed interpreter
140 without regard to the setting of environment variables such as
141 .Ev PATH .
142 This makes it somewhat challenging to set the
143 .Sq #!
144 line of a script so that it will run identically on different systems.
145 .Pp
146 Since the
147 .Xr env 1
148 utility executes a command passed to it on its command line, it is
149 often used as a
150 .Dq trampoline
151 to render scripts portable.
152 If the leading line of a script reads
153 .Pp
154 .Dl #! /usr/bin/env interp
155 .Pp
156 then the
157 .Xr env 1
158 command will execute the
159 .Dq interp
160 command it finds in its
161 .Ev PATH ,
162 passing on to it all subsequent arguments with which it itself was called.
163 Since
164 .Pa /usr/bin/env
165 is found on almost all
166 .Tn POSIX
167 style systems, this trick is frequently exploited by authors who need
168 a script to execute without change on multiple systems.
169 .Ss Historical Note: Scripts without `#!'
170 Shell scripts predate the invention of the
171 .Sq #!
172 convention, which is implemented in the kernel.
173 In the days of
174 .At v7 ,
175 there was only one interpreter used on the system,
176 .Pa /bin/sh ,
177 and the shell treated any file that failed to execute with an
178 .Er ENOEXEC
179 error
180 (see
181 .Xr intro 2 )
182 as a shell script.
183 .Pp
184 Most shells (such as
185 .Xr sh 1 )
186 and certain other facilities (including
187 .Xr execlp 3
188 and
189 .Xr execvp 3
190 but not other types of
191 .Xr exec 3
192 calls) still pass
193 interpreter scripts that do not include the
194 .Sq #!
195 (and thus fail to execute with
196 .Er ENOEXEC )
197 to
198 .Pa /bin/sh .
199 .Pp
200 As this behavior is implemented outside the kernel, there is no
201 mechanism that forces it to be respected by all programs that execute
202 other programs.
203 It is thus not completely reliable.
204 It is therefore important to always include
205 .Pp
206 .Dl #!/bin/sh
207 .Pp
208 in front of Bourne shell scripts, and to treat the traditional
209 behavior as obsolete.
210 .Sh EXAMPLES
211 Suppose that an executable binary exists in
212 .Pa /bin/interp
213 and that the file
214 .Pa /tmp/script
215 contains:
216 .Bd -literal -offset indent
217 #!/bin/interp -arg
218
219 [...]
220 .Ed
221 .Pp
222 and that
223 .Pa /tmp/script
224 is set mode 755.
225 .Pp
226 Executing
227 .Pp
228 .Dl $ /tmp/script one two three
229 .Pp
230 at the shell will result in
231 .Pa /bin/interp
232 being executed, receiving the following arguments in
233 .Va argv
234 (numbered from 0):
235 .Bd -ragged -offset indent
236 .Qq /bin/interp ,
237 .Qq "-arg" ,
238 .Qq /tmp/script ,
239 .Qq one ,
240 .Qq two ,
241 .Qq three
242 .Ed
243 .Ss Portability Note: Multiple arguments
244 The behavior of multiple arguments on the
245 .Sq #!
246 line is highly non-portable between different systems.
247 In general, only one argument can be assumed to work consistently.
248 .Pp
249 Consider the following variation on the previous example.
250 Suppose that an executable binary exists in
251 .Pa /bin/interp
252 and that the file
253 .Pa /tmp/script
254 contains:
255 .Bd -literal -offset indent
256 #!/bin/interp -x -y
257
258 [...]
259 .Ed
260 .Pp
261 and that
262 .Pa /tmp/script
263 is set mode 755.
264 .Pp
265 Executing
266 .Pp
267 .Dl $ /tmp/script one two three
268 .Pp
269 at the shell will result in
270 .Pa /bin/interp
271 being executed, receiving the following arguments in
272 .Va argv
273 (numbered from 0):
274 .Bd -ragged -offset indent
275 .Qq /bin/interp ,
276 .Qq "-x -y" ,
277 .Qq /tmp/script ,
278 .Qq one ,
279 .Qq two ,
280 .Qq three
281 .Ed
282 .Pp
283 Note that
284 .Qq "-x -y"
285 will be passed on
286 .Dx
287 as a single argument.
288 .Pp
289 Although most
290 .Tn POSIX
291 style operating systems will pass only one
292 .Ar argument ,
293 the behavior when multiple arguments are included is not
294 consistent between platforms.
295 Some, such as
296 .Dx ,
297 will concatenate multiple arguments into a single argument (as above),
298 some will truncate them, and at least one will pass them as multiple
299 arguments.
300 .Pp
301 The
302 .Dx
303 behavior is common but not universal.
304 Sun's
305 .Tn Solaris
306 would present the above argument as
307 .Qq -x ,
308 dropping the
309 .Qq " -y"
310 entirely.
311 Perhaps uniquely, recent versions of Apple's
312 .Tn OS X
313 will actually pass multiple arguments properly, i.e.:
314 .Bd -ragged -offset indent
315 .Qq /bin/interp ,
316 .Qq -x ,
317 .Qq -y ,
318 .Qq /tmp/script ,
319 .Qq one ,
320 .Qq two ,
321 .Qq three
322 .Ed
323 .Pp
324 The behavior of the system in the face of multiple arguments is thus
325 not currently standardized, should not be relied on, and may be
326 changed in future releases.
327 In general, pass at most one argument, and do not rely on multiple
328 arguments being concatenated.
329 .Sh SEE ALSO
330 .Xr awk 1 ,
331 .Xr csh 1 ,
332 .Xr sh 1 ,
333 .Xr chmod 2 ,
334 .Xr execve 2 ,
335 .Xr intro 2 ,
336 .Xr execlp 3 ,
337 .Xr execvp 3
338 .Sh STANDARDS
339 The behavior of interpreter scripts is obliquely referred to, but
340 never actually described in,
341 .St -p1003.1-2004 .
342 .Pp
343 The behavior is partially (but not completely) described in the
344 .St -svid4 .
345 .Pp
346 Although it has never been formally standardized, the behavior
347 described is largely portable across
348 .Tn POSIX
349 style systems, with two significant exceptions: the maximum length of the
350 .Sq #!
351 line, and the behavior if multiple arguments are passed.
352 Please be aware that the behavior in the
353 face of multiple arguments is not consistent across systems.
354 .Sh HISTORY
355 The behavior of the kernel when encountering scripts that start in
356 .Sq #!
357 was not present in
358 .At v7 .
359 A Usenet posting to net.unix by Guy Harris on October 16, 1984 claims
360 that the idea for the
361 .Sq #!
362 behavior was first proposed by Dennis Ritchie but that the first
363 implementation was on
364 .Bx .
365 .Pp
366 Historical manuals (specifically the exec man page) indicate that the
367 behavior was present in
368 .Bx 4
369 at least as early as April, 1981.
370 Information on precisely when it was first implemented, and in which
371 version of
372 .Ux ,
373 is solicited.
374 .Sh CAVEATS
375 Numerous security problems are associated with setuid interpreter
376 scripts.
377 .Pp
378 In addition to the fact that many interpreters (and scripts) are
379 simply not designed to be robust in a setuid context, a race condition
380 exists between the moment that the kernel examines the interpreter
381 script file and the moment that the newly invoked interpreter opens
382 the file itself.
383 .Pp
384 Subtle techniques can be used to subvert even seemingly well written scripts.
385 Scripts executed by Bourne type shells can be subverted in numerous
386 ways, such as by setting the
387 .Ev IFS
388 variable before executing the script.
389 Other interpreters possess their own vulnerabilities.
390 Setting the Set-user-ID on execution (SUID) bit
391 is therefore very dangerous, and should not be done lightly, if at all.