[ci skip] multi-user should be multiuser
[scons.git] / doc / user / install.xml
blob16e1a72358bc8c90f1983a38870e382b124e7a25
1 <?xml version='1.0'?>
3 <!--
4 SPDX-FileCopyrightText: Copyright The SCons Foundation (https://scons.org)
5 SPDX-License-Identifier: MIT
6 SPDX-FileType: DOCUMENTATION
8 This file is processed by the bin/SConsDoc.py module.
9 -->
11 <!DOCTYPE sconsdoc [
12     <!ENTITY % scons SYSTEM "../scons.mod">
13     %scons;
15     <!ENTITY % builders-mod SYSTEM "../generated/builders.mod">
16     %builders-mod;
17     <!ENTITY % functions-mod SYSTEM "../generated/functions.mod">
18     %functions-mod;
19     <!ENTITY % tools-mod SYSTEM "../generated/tools.mod">
20     %tools-mod;
21     <!ENTITY % variables-mod SYSTEM "../generated/variables.mod">
22     %variables-mod;
26 <chapter id="chap-install"
27          xmlns="http://www.scons.org/dbxsd/v1.0"
28          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
29          xsi:schemaLocation="http://www.scons.org/dbxsd/v1.0 http://www.scons.org/dbxsd/v1.0/scons.xsd">
30 <title>Installing Files in Other Directories:  the &Install; Builder</title>
32   <para>
34   Once a program is built,
35   it is often appropriate to install it in another
36   directory for public use.
37   You use the &Install; method
38   to arrange for a program, or any other file,
39   to be copied into a destination directory:
41   </para>
43   <scons_example name="install_ex1">
44      <file name="SConstruct" printme="1">
45 env = Environment()
46 hello = env.Program('hello.c')
47 env.Install('__ROOT__/usr/bin', hello)
48      </file>
49      <file name="hello.c">
50 int main() { printf("Hello, world!\n"); }
51      </file>
52   </scons_example>
54   <para>
56   Note, however, that installing a file is
57   still considered a type of file "build."
58   This is important when you remember that
59   the default behavior of &SCons; is
60   to build files in or below the current directory.
61   If, as in the example above,
62   you are installing files in a directory
63   outside of the top-level &SConstruct; file's directory tree,
64   you must specify that directory
65   (or a higher directory, such as <literal>/</literal>)
66   for it to install anything there:
68   </para>
70   <scons_output example="install_ex1" suffix="1">
71      <scons_output_command>scons -Q</scons_output_command>
72      <scons_output_command>scons -Q __ROOT__/usr/bin</scons_output_command>
73   </scons_output>
75   <para>
77   It can, however, be cumbersome to remember
78   (and type) the specific destination directory
79   in which the program (or other file)
80   should be installed.  A call to &Default; can be used to
81   add the directory to the list of default targets,
82   removing the need to type it,
83   but sometimes you don't want to install on every build.
84   This is an area where the &Alias;
85   function comes in handy,
86   allowing you, for example,
87   to create a pseudo-target named <literal>install</literal>
88   that can expand to the specified destination directory:
90   </para>
92   <scons_example name="install_ex2">
93     <file name="SConstruct" printme="1">
94 env = Environment()
95 hello = env.Program('hello.c')
96 env.Install('__ROOT__/usr/bin', hello)
97 env.Alias('install', '__ROOT__/usr/bin')
98     </file>
99     <file name="hello.c">
100 int main() { printf("Hello, world!\n"); }
101     </file>
102   </scons_example>
104   <para>
106   This then yields the more natural
107   ability to install the program
108   in its destination as a separate
109   invocation, as follows:
111   </para>
113   <scons_output example="install_ex2" suffix="1">
114      <scons_output_command>scons -Q</scons_output_command>
115      <scons_output_command>scons -Q install</scons_output_command>
116   </scons_output>
118   <section>
119   <title>Installing Multiple Files in a Directory</title>
121     <para>
123     You can install multiple files into a directory
124     simply by calling the &Install; function multiple times:
126     </para>
128     <scons_example name="install_ex3">
129       <file name="SConstruct" printme="1">
130 env = Environment()
131 hello = env.Program('hello.c')
132 goodbye = env.Program('goodbye.c')
133 env.Install('__ROOT__/usr/bin', hello)
134 env.Install('__ROOT__/usr/bin', goodbye)
135 env.Alias('install', '__ROOT__/usr/bin')
136       </file>
137       <file name="hello.c">
138 int main() { printf("Hello, world!\n"); }
139       </file>
140       <file name="goodbye.c">
141 int main() { printf("Goodbye, world!\n"); }
142       </file>
143     </scons_example>
145     <para>
147     Or, more succinctly, listing the multiple input
148     files in a list
149     (just like you can do with any other builder):
151     </para>
153     <sconstruct>
154 env = Environment()
155 hello = env.Program('hello.c')
156 goodbye = env.Program('goodbye.c')
157 env.Install('__ROOT__/usr/bin', [hello, goodbye])
158 env.Alias('install', '__ROOT__/usr/bin')
159     </sconstruct>
161     <para>
163     Either of these two examples yields:
165     </para>
167     <scons_output example="install_ex3" suffix="1">
168        <scons_output_command>scons -Q install</scons_output_command>
169     </scons_output>
171   </section>
173   <section>
174   <title>Installing a File Under a Different Name</title>
176     <para>
178     The &Install; method preserves the name
179     of the file when it is copied into the
180     destination directory.
181     If you need to change the name of the file
182     when you copy it, use the &InstallAs; function:
184     </para>
186     <scons_example name="install_ex4">
187       <file name="SConstruct" printme="1">
188 env = Environment()
189 hello = env.Program('hello.c')
190 env.InstallAs('__ROOT__/usr/bin/hello-new', hello)
191 env.Alias('install', '__ROOT__/usr/bin')
192       </file>
193       <file name="hello.c">
194 int main() { printf("Hello, world!\n"); }
195       </file>
196     </scons_example>
198     <para>
200     This installs the <literal>hello</literal>
201     program with the name <literal>hello-new</literal>
202     as follows:
204     </para>
206     <scons_output example="install_ex4" suffix="1">
207        <scons_output_command>scons -Q install</scons_output_command>
208     </scons_output>
210   </section>
212   <section>
213   <title>Installing Multiple Files Under Different Names</title>
215     <para>
217     If you have multiple files that all
218     need to be installed with different file names,
219     you can either call the &InstallAs; function
220     multiple times, or as a shorthand,
221     you can supply same-length lists
222     for both the target and source arguments:
224     </para>
226     <scons_example name="install_ex5">
227       <file name="SConstruct" printme="1">
228 env = Environment()
229 hello = env.Program('hello.c')
230 goodbye = env.Program('goodbye.c')
231 env.InstallAs(['__ROOT__/usr/bin/hello-new',
232                '__ROOT__/usr/bin/goodbye-new'],
233                [hello, goodbye])
234 env.Alias('install', '__ROOT__/usr/bin')
235       </file>
236       <file name="hello.c">
237 int main() { printf("Hello, world!\n"); }
238       </file>
239       <file name="goodbye.c">
240 int main() { printf("Goodbye, world!\n"); }
241       </file>
242     </scons_example>
244     <para>
246     In this case, the &InstallAs; function
247     loops through both lists simultaneously,
248     and copies each source file into its corresponding
249     target file name:
251     </para>
253     <scons_output example="install_ex5" suffix="1">
254        <scons_output_command>scons -Q install</scons_output_command>
255     </scons_output>
257   </section>
259   <section>
260   <title>Installing a Shared Library</title>
262     <para>
263     If a shared library is created with the
264     &cv-link-SHLIBVERSION; variable set,
265     &scons; will create symbolic links as needed based on that
266     variable.  To properly install such a library including the
267     symbolic links, use the &InstallVersionedLib; function.
268     </para>
270     <para>
271     For example, on a Linux system, this instruction:
272     </para>
274     <sconstruct>
275 foo =  env.SharedLibrary(target="foo", source="foo.c", SHLIBVERSION="1.2.3")
276     </sconstruct>
278     <para>
279     Will produce a shared library
280     <filename>libfoo.so.1.2.3</filename>
281     and symbolic links
282     <filename>libfoo.so</filename> and
283     <filename>libfoo.so.1</filename>
284     which point to
285     <filename>libfoo.so.1.2.3</filename>.
286     You can use the Node returned by the &SharedLibrary;
287     builder in order to install the library and its
288     symbolic links in one go without having to list
289     them individually:
290     </para>
292     <sconstruct>
293 env.InstallVersionedLib(target="lib", source=foo)
294     </sconstruct>
296 <!-- didn't get this to illustrate what I expected: example reports
297      installing lib without version, while manual effort has it:
299     <scons_example name="install_ex6">
300       <file name="SConstruct" printme="1">
301 env = Environment()
302 foo =  env.SharedLibrary(target="foo", source="foo.c", SHLIBVERSION="1.2.3")
303 ins = env.InstallVersionedLib(target="lib", source=foo)
304 env.Alias('install', ins)
305       </file>
306       <file name="foo.c">
307 int call_foo() {
308     printf("Hello world");
309     return(0);
311       </file>
312     </scons_example>
314     <scons_output example="install_ex6" suffix="1">
315        <scons_output_command>scons -Q install</scons_output_command>
316     </scons_output>
319   <para>
320   On systems which expect a shared library to be installed both with
321   a name that indicates the version, for run-time resolution,
322   and as a plain name, for link-time resolution, the
323   &InstallVersionedLib; function can be used.  Symbolic links
324   appropriate to the type of system will be generated based on
325   symlinks of the source library.
326   </para>
327   </section>
329 </chapter>