yield: Implement for OS/2 kLIBC.
[gnulib.git] / doc / relocatable-maint.texi
blobd39159810899dc3871964f7ebcdd2b169869e4b6
1 @node Supporting Relocation
2 @section Supporting Relocation
4 It has been a pain for many users of GNU packages for a long time that
5 packages are not relocatable.  It means a user cannot copy a program,
6 installed by another user on the same machine, to his home directory,
7 and have it work correctly (including i18n).  So many users need to go
8 through @code{configure; make; make install} with all its
9 dependencies, options, and hurdles.
11 Red Hat, Debian, and other binary distributions solve the ``ease of
12 installation'' problem, but they hardwire path names, usually to
13 @file{/usr} or @file{/usr/local}.  This means that users need root
14 privileges to install a binary package, and prevents installing two
15 different versions of the same binary package.
17 A relocatable program can be moved or copied to a different location
18 on the file system.  It is possible to make symlinks to the installed
19 and moved programs, and invoke them through the symlink. It is
20 possible to do the same thing with a hard link @emph{only} if the hard
21 link file is in the same directory as the real program.
23 The @code{relocatable-prog} module aims to ease the process of making a
24 GNU program relocatable.  It helps overcome two obstacles.  First, it aids
25 with relocating the hard-coded references to absolute file names that
26 GNU programs often contain.  These references must be fixed up at
27 runtime if a program is to be successfully relocated.  The
28 @code{relocatable-prog} module provides a function @code{relocate} that
29 does this job.
31 Second, the loader must be able to find shared libraries linked to
32 relocatable executables or referenced by other shared libraries linked
33 to relocatable executables.  The @code{relocatable-prog} module helps out
34 here in a platform-specific way:
36 @itemize
37 @item
38 On most operating systems, it adds a linker option (@option{-rpath}) that
39 causes the dynamic linker to search for libraries in a directory relative
40 to the location of the invoked executable.  This works on GNU/Linux and
41 modern versions of GNU/Hurd, GNU/kFreeBSD, macOS, FreeBSD, NetBSD, OpenBSD,
42 Solaris, Haiku.
44 @item
45 On other Unix systems, it installs a trampoline executable.  The trampoline
46 sets the environment variable that controls shared library searching
47 (usually @env{LD_LIBRARY_PATH}) and then invokes the real executable.
48 This applies to operating systems such as AIX, HP-UX, or Minix.
50 @item
51 On Windows, the executable's own directory is searched for libraries,
52 so installing shared libraries into the executable's directory is
53 sufficient.
54 @end itemize
56 You can make your program relocatable by following these steps:
58 @enumerate
59 @item
60 Import the @code{relocatable-prog} module.  For libraries, use the
61 @code{relocatable-lib} or @code{relocatable-lib-lgpl} module, if
62 the libraries are independent.  For installing multiple libraries,
63 at least one of which depends on another one, use the @code{relocatable-prog}
64 module.
65 If you need more than one module, or you need to use them with different
66 settings, you will need multiple copies of gnulib (@pxref{Multiple instances}).
68 @item
69 In every program, add to @code{main} as the first statement (even
70 before setting the locale or doing anything related to libintl):
72 @example
73 set_program_name (argv[0]);
74 @end example
76 The prototype for this function is in @file{progname.h}.
78 @item
79 If you want your code to be portable to platforms that do not support
80 automatic initialization, call @code{set_relocation_prefix}.
82 @item
83 Everywhere where you use a constant pathname from installation-time,
84 wrap it in @code{relocate} so it gets translated to the run-time situation.
85 Example:
87 @example
88 bindtextdomain (PACKAGE, LOCALEDIR);
89 @end example
91 @noindent
92 becomes:
94 @example
95 bindtextdomain (PACKAGE, relocate (LOCALEDIR));
96 @end example
98 The prototype for this function is in @file{relocatable.h}.
100 There is also a variant of this function, named @code{relocate2}, that
101 makes it easy to reclaim the memory allocated by the call.
103 @item
104 The @code{set_program_name} function can also configure some
105 additional libraries to relocate files that they access, by defining
106 corresponding C preprocessor symbols to 1.  The libraries for which
107 this is supported and the corresponding preprocessor symbols are:
109 @table @asis
110 @item libcharset
111 @code{DEPENDS_ON_LIBCHARSET}
113 @item libiconv
114 @code{DEPENDS_ON_LIBICONV}
116 @item libintl
117 @code{DEPENDS_ON_LIBINTL}
118 @end table
120 Defining the symbol for a library makes every program in the package
121 depend on that library, whether the program really uses the library or
122 not, so this feature should be used with some caution.
124 @item
125 If your package installs shell scripts, also import the
126 @code{relocatable-script} module.  Then, near the beginning of each
127 shell script that your package installs, add the following:
129 @smallexample
130 @@relocatable_sh@@
132 prefix="@@prefix@@"
133 exec_prefix="@@exec_prefix@@"   # usually needs $prefix.
134 datarootdir="@@datarootdir@@"   # usually needs $prefix.
136 if test "@@RELOCATABLE@@" = yes; then
137   bindir="@@bindir@@"
138   orig_installdir="$bindir" # see Makefile.am's *_SCRIPTS variables
139   func_find_curr_installdir # determine curr_installdir
140   func_find_prefixes
141   relocate () @{
142     echo "$1/" \
143     | sed -e "s%^$@{orig_installprefix@}/%$@{curr_installprefix@}/%" \
144     | sed -e 's,/$,,'
145   @}
146 else
147   relocate () @{
148     echo "$1"
149   @}
152 # Get some relocated directory names.
153 sysconfdir=`relocate "@@sysconfdir@@"`          # usually needs $prefix.
154 some_datadir=`relocate "@@datadir@@/something"` # usually needs $datarootdir.
155 bindir=`relocate "@@bindir@@"`       # usually needs $exec_prefix, hence $prefix.
156 @end smallexample
158 You must adapt the definition of @code{orig_installdir}, depending on
159 where the script gets installed.  Also, at the end, instead of
160 @code{sysconfdir} and @code{some_datadir}, transform those variables
161 that you need.
163 @item
164 If your package installs Perl scripts, also import the
165 @code{relocatable-perl} module.  Then, near the beginning of each
166 Perl script that your package installs, add the following:
168 @smallexample
169 @@relocatable_pl@@
170 if ("@@RELOCATABLE@@" eq "yes") @{
171   my $exec_prefix = "@@exec_prefix@@";
172   my $orig_installdir = "@@bindir@@"; # see Makefile.am's *_SCRIPTS variables
173   my ($orig_installprefix, $curr_installprefix) =
174     find_prefixes($orig_installdir, find_curr_installdir());
176   # the subroutine is defined whether or not the enclosing block is executed
177   sub relocate @{
178     my ($dir) = @@_;
179     if ("@@RELOCATABLE@@" eq "yes") @{
180       $dir =~ s%^$orig_installprefix/%$curr_installprefix/%;
181       $dir =~ s,/$,,;
182     @}
183     return $dir;
184   @}
187 # Get some relocated directory names.
188 # (The gnulib module 'configmake' can help with this.)
189 $sysconfdir = relocate("@@sysconfdir@@");
190 $some_datadir = relocate(@@datadir@@/something");
191 @end smallexample
193 You must adapt the definition of @code{$orig_installdir}, depending on
194 where the script gets installed.  Also, at the end, instead of
195 @code{sysconfdir} and @code{some_datadir}, transform those variables
196 that you need.
198 @item
199 In your @file{Makefile.am}, for every program @command{foo} that gets
200 installed in, say, @file{$(bindir)}, you add:
202 @example
203 foo_CPPFLAGS = -DINSTALLDIR=\"$(bindir)\"
204 if RELOCATABLE_VIA_LD
205 foo_LDFLAGS = `$(RELOCATABLE_LDFLAGS) $(bindir)`
206 endif
207 @end example
209 When building gnulib to use with a relocatable library, you need to
210 define the preprocessor symbol @code{IN_LIBRARY}.
211 You may also want to build with @code{ENABLE_COSTLY_RELOCATABLE}, in which case
212 you will also need to define @code{INSTALLDIR}.
213 The following fragment can be added to an override @code{Makefile.am} used
214 to build gnulib (@pxref{Modified build rules}).
216 @example
217 AM_CPPFLAGS += -DIN_LIBRARY -DENABLE_COSTLY_RELOCATABLE
219 if SHLIBS_IN_BINDIR
220 AM_CPPFLAGS += -DINSTALLDIR=\"$(bindir)\"
221 else
222 AM_CPPFLAGS += -DINSTALLDIR=\"$(libdir)\"
223 endif
224 @end example
226 @code{SHLIBS_IN_BINDIR} is defined in @file{configure.ac} as follows:
228 @smallexample
229 AM_CONDITIONAL([SHLIBS_IN_BINDIR],
230                [case "$host_os" in mingw* | cygwin*) true;; *) false;; esac])
231 @end smallexample
233 @item
234 In your @file{Makefile.am}, for every library @command{libfoo} that gets
235 installed in, say, @file{$(libdir)}, you add:
237 @example
238 if RELOCATABLE_VIA_LD
239 libfoo_la_LDFLAGS = `$(RELOCATABLE_LDFLAGS) $(libdir)`
240 endif
241 @end example
243 @item
244 Add a couple of variable assignments to your @file{Makefile.am}.
246 If your package (or any package you rely on, e.g.@: gettext-runtime)
247 will be relocated together with a set of installed shared libraries,
248 then set @code{RELOCATABLE_LIBRARY_PATH} to a colon-separated list
249 of those libraries' directories, e.g.
250 @example
251 RELOCATABLE_LIBRARY_PATH = $(libdir)
252 @end example
254 If your @file{config.h} is not in @file{$(top_builddir)}, then set
255 @code{RELOCATABLE_CONFIG_H_DIR} to its directory, e.g.
256 @example
257 RELOCATABLE_CONFIG_H_DIR = $(top_builddir)/src
258 @end example
259 @end enumerate