]> git.ipfire.org Git - thirdparty/glibc.git/blob - elf/ldconfig.c
install.texi: Build was tested with binutils 2.41 (just released)
[thirdparty/glibc.git] / elf / ldconfig.c
1 /* Copyright (C) 1999-2023 Free Software Foundation, Inc.
2 This file is part of the GNU C Library.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published
6 by the Free Software Foundation; version 2 of the License, or
7 (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, see <https://www.gnu.org/licenses/>. */
16
17 #define PROCINFO_CLASS static
18 #include <assert.h>
19 #include <alloca.h>
20 #include <argp.h>
21 #include <dirent.h>
22 #include <elf.h>
23 #include <error.h>
24 #include <errno.h>
25 #include <inttypes.h>
26 #include <libintl.h>
27 #include <locale.h>
28 #include <stdbool.h>
29 #include <stdio.h>
30 #include <stdio_ext.h>
31 #include <stdlib.h>
32 #include <string.h>
33 #include <unistd.h>
34 #include <stdint.h>
35 #include <sys/fcntl.h>
36 #include <sys/mman.h>
37 #include <sys/stat.h>
38 #include <sys/types.h>
39 #include <glob.h>
40 #include <libgen.h>
41
42 #include <ldconfig.h>
43 #include <dl-cache.h>
44 #include <dl-hwcaps.h>
45 #include <dl-is_dso.h>
46
47 #include <dl-procinfo.h>
48
49 #ifndef LD_SO_CONF
50 # define LD_SO_CONF SYSCONFDIR "/ld.so.conf"
51 #endif
52
53 /* Get libc version number. */
54 #include <version.h>
55
56 #define PACKAGE _libc_intl_domainname
57
58 /* List of directories to handle. */
59 struct dir_entry
60 {
61 char *path;
62 int flag;
63 ino64_t ino;
64 dev_t dev;
65 const char *from_file;
66 int from_line;
67
68 /* Non-NULL for subdirectories under a glibc-hwcaps subdirectory. */
69 struct glibc_hwcaps_subdirectory *hwcaps;
70
71 struct dir_entry *next;
72 };
73
74 /* The list is unsorted, contains no duplicates. Entries are added at
75 the end. */
76 static struct dir_entry *dir_entries;
77
78 /* Flags for different options. */
79 /* Print Cache. */
80 static int opt_print_cache;
81
82 /* Be verbose. */
83 int opt_verbose;
84
85 /* Format to support. */
86 enum opt_format opt_format = opt_format_new;
87
88 /* Build cache. */
89 static int opt_build_cache = 1;
90
91 /* Enable symbolic link processing. If set, create or update symbolic
92 links, and remove stale symbolic links. */
93 static int opt_link = 1;
94
95 /* Only process directories specified on the command line. */
96 static int opt_only_cline;
97
98 /* Path to root for chroot. */
99 static char *opt_chroot;
100
101 /* Manually link given shared libraries. */
102 static int opt_manual_link;
103
104 /* Should we ignore an old auxiliary cache file? */
105 static int opt_ignore_aux_cache;
106
107 /* Cache file to use. */
108 static char *cache_file;
109
110 /* Configuration file. */
111 static const char *config_file;
112
113 /* Name and version of program. */
114 static void print_version (FILE *stream, struct argp_state *state);
115 void (*argp_program_version_hook) (FILE *, struct argp_state *)
116 = print_version;
117
118 /* Function to print some extra text in the help message. */
119 static char *more_help (int key, const char *text, void *input);
120
121 /* Definitions of arguments for argp functions. */
122 static const struct argp_option options[] =
123 {
124 { "print-cache", 'p', NULL, 0, N_("Print cache"), 0},
125 { "verbose", 'v', NULL, 0, N_("Generate verbose messages"), 0},
126 { NULL, 'N', NULL, 0, N_("Don't build cache"), 0},
127 { NULL, 'X', NULL, 0, N_("Don't update symbolic links"), 0},
128 { NULL, 'r', N_("ROOT"), 0, N_("Change to and use ROOT as root directory"), 0},
129 { NULL, 'C', N_("CACHE"), 0, N_("Use CACHE as cache file"), 0},
130 { NULL, 'f', N_("CONF"), 0, N_("Use CONF as configuration file"), 0},
131 { NULL, 'n', NULL, 0, N_("Only process directories specified on the command line. Don't build cache."), 0},
132 { NULL, 'l', NULL, 0, N_("Manually link individual libraries."), 0},
133 { "format", 'c', N_("FORMAT"), 0, N_("Format to use: new (default), old, or compat"), 0},
134 { "ignore-aux-cache", 'i', NULL, 0, N_("Ignore auxiliary cache file"), 0},
135 { NULL, 0, NULL, 0, NULL, 0 }
136 };
137
138 #define PROCINFO_CLASS static
139 #include <dl-procinfo.c>
140
141 /* Short description of program. */
142 static const char doc[] = N_("Configure Dynamic Linker Run Time Bindings.");
143
144 /* Prototype for option handler. */
145 static error_t parse_opt (int key, char *arg, struct argp_state *state);
146
147 /* Data structure to communicate with argp functions. */
148 static struct argp argp =
149 {
150 options, parse_opt, NULL, doc, NULL, more_help, NULL
151 };
152
153 /* Handle program arguments. */
154 static error_t
155 parse_opt (int key, char *arg, struct argp_state *state)
156 {
157 switch (key)
158 {
159 case 'C':
160 cache_file = arg;
161 /* Ignore auxiliary cache since we use non-standard cache. */
162 opt_ignore_aux_cache = 1;
163 break;
164 case 'f':
165 config_file = arg;
166 break;
167 case 'i':
168 opt_ignore_aux_cache = 1;
169 break;
170 case 'l':
171 opt_manual_link = 1;
172 break;
173 case 'N':
174 opt_build_cache = 0;
175 break;
176 case 'n':
177 opt_build_cache = 0;
178 opt_only_cline = 1;
179 break;
180 case 'p':
181 opt_print_cache = 1;
182 break;
183 case 'r':
184 opt_chroot = arg;
185 break;
186 case 'v':
187 opt_verbose = 1;
188 break;
189 case 'X':
190 opt_link = 0;
191 break;
192 case 'c':
193 if (strcmp (arg, "old") == 0)
194 opt_format = opt_format_old;
195 else if (strcmp (arg, "compat") == 0)
196 opt_format = opt_format_compat;
197 else if (strcmp (arg, "new") == 0)
198 opt_format = opt_format_new;
199 break;
200 default:
201 return ARGP_ERR_UNKNOWN;
202 }
203
204 return 0;
205 }
206
207 /* Print bug-reporting information in the help message. */
208 static char *
209 more_help (int key, const char *text, void *input)
210 {
211 char *tp = NULL;
212 switch (key)
213 {
214 case ARGP_KEY_HELP_EXTRA:
215 /* We print some extra information. */
216 if (asprintf (&tp, gettext ("\
217 For bug reporting instructions, please see:\n\
218 %s.\n"), REPORT_BUGS_TO) < 0)
219 return NULL;
220 return tp;
221 default:
222 break;
223 }
224 return (char *) text;
225 }
226
227 /* Print the version information. */
228 static void
229 print_version (FILE *stream, struct argp_state *state)
230 {
231 fprintf (stream, "ldconfig %s%s\n", PKGVERSION, VERSION);
232 fprintf (stream, gettext ("\
233 Copyright (C) %s Free Software Foundation, Inc.\n\
234 This is free software; see the source for copying conditions. There is NO\n\
235 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\
236 "), "2023");
237 fprintf (stream, gettext ("Written by %s.\n"),
238 "Andreas Jaeger");
239 }
240
241 /* Allocate a new subdirectory with full path PATH under ENTRY, using
242 inode data from *ST. */
243 static struct dir_entry *
244 new_sub_entry (const struct dir_entry *entry, const char *path,
245 const struct stat *st)
246 {
247 struct dir_entry *new_entry = xmalloc (sizeof (struct dir_entry));
248 new_entry->from_file = entry->from_file;
249 new_entry->from_line = entry->from_line;
250 new_entry->path = xstrdup (path);
251 new_entry->flag = entry->flag;
252 new_entry->hwcaps = NULL;
253 new_entry->next = NULL;
254 new_entry->ino = st->st_ino;
255 new_entry->dev = st->st_dev;
256 return new_entry;
257 }
258
259 /* Add a single directory entry. Return true if the directory is
260 actually added (because it is not a duplicate). */
261 static bool
262 add_single_dir (struct dir_entry *entry, int verbose)
263 {
264 struct dir_entry *ptr, *prev;
265 bool added = true;
266
267 ptr = dir_entries;
268 prev = ptr;
269 while (ptr != NULL)
270 {
271 /* Check for duplicates. */
272 if (ptr->ino == entry->ino && ptr->dev == entry->dev)
273 {
274 if (opt_verbose && verbose)
275 {
276 error (0, 0, _("Path `%s' given more than once"), entry->path);
277 fprintf (stderr, _("(from %s:%d and %s:%d)\n"),
278 entry->from_file, entry->from_line,
279 ptr->from_file, ptr->from_line);
280 }
281 /* Use the newer information. */
282 ptr->flag = entry->flag;
283 free (entry->path);
284 free (entry);
285 added = false;
286 break;
287 }
288 prev = ptr;
289 ptr = ptr->next;
290 }
291 /* Is this the first entry? */
292 if (ptr == NULL && dir_entries == NULL)
293 dir_entries = entry;
294 else if (ptr == NULL)
295 prev->next = entry;
296 return added;
297 }
298
299 /* Check if PATH contains a "glibc-hwcaps" subdirectory. If so, queue
300 its subdirectories for glibc-hwcaps processing. */
301 static void
302 add_glibc_hwcaps_subdirectories (struct dir_entry *entry, const char *path)
303 {
304 /* glibc-hwcaps subdirectories do not nest. */
305 assert (entry->hwcaps == NULL);
306
307 char *glibc_hwcaps;
308 if (asprintf (&glibc_hwcaps, "%s/" GLIBC_HWCAPS_SUBDIRECTORY, path) < 0)
309 error (EXIT_FAILURE, errno, _("Could not form glibc-hwcaps path"));
310
311 DIR *dir = opendir (glibc_hwcaps);
312 if (dir != NULL)
313 {
314 while (true)
315 {
316 errno = 0;
317 struct dirent64 *e = readdir64 (dir);
318 if (e == NULL)
319 {
320 if (errno == 0)
321 break;
322 else
323 error (EXIT_FAILURE, errno, _("Listing directory %s"), path);
324 }
325
326 /* Ignore hidden subdirectories, including "." and "..", and
327 regular files. File names containing a ':' cannot be
328 looked up by the dynamic loader, so skip those as
329 well. */
330 if (e->d_name[0] == '.' || e->d_type == DT_REG
331 || strchr (e->d_name, ':') != NULL)
332 continue;
333
334 /* See if this entry eventually resolves to a directory. */
335 struct stat st;
336 if (fstatat (dirfd (dir), e->d_name, &st, 0) < 0)
337 /* Ignore unreadable entries. */
338 continue;
339
340 if (S_ISDIR (st.st_mode))
341 {
342 /* This is a directory, so it needs to be scanned for
343 libraries, associated with the hwcaps implied by the
344 subdirectory name. */
345 char *new_path;
346 if (asprintf (&new_path, "%s/" GLIBC_HWCAPS_SUBDIRECTORY "/%s",
347 /* Use non-canonicalized path here. */
348 entry->path, e->d_name) < 0)
349 error (EXIT_FAILURE, errno,
350 _("Could not form glibc-hwcaps path"));
351 struct dir_entry *new_entry = new_sub_entry (entry, new_path,
352 &st);
353 free (new_path);
354 new_entry->hwcaps = new_glibc_hwcaps_subdirectory (e->d_name);
355 add_single_dir (new_entry, 0);
356 }
357 }
358
359 closedir (dir);
360 }
361
362 free (glibc_hwcaps);
363 }
364
365 /* Add one directory to the list of directories to process. */
366 static void
367 add_dir_1 (const char *line, const char *from_file, int from_line)
368 {
369 unsigned int i;
370 struct dir_entry *entry = xmalloc (sizeof (struct dir_entry));
371 entry->hwcaps = NULL;
372 entry->next = NULL;
373
374 entry->from_file = strdup (from_file);
375 entry->from_line = from_line;
376
377 entry->path = xstrdup (line);
378 entry->flag = FLAG_ELF_LIBC6;
379
380 /* Canonify path: for now only remove leading and trailing
381 whitespace and the trailing slashes. */
382 i = strlen (entry->path);
383
384 while (i > 0 && isspace (entry->path[i - 1]))
385 entry->path[--i] = '\0';
386
387 while (i > 0 && entry->path[i - 1] == '/')
388 entry->path[--i] = '\0';
389
390 if (i == 0)
391 {
392 free (entry->path);
393 free (entry);
394 return;
395 }
396
397 char *path = entry->path;
398 if (opt_chroot != NULL)
399 path = chroot_canon (opt_chroot, path);
400
401 struct stat stat_buf;
402 if (path == NULL || stat (path, &stat_buf))
403 {
404 if (opt_verbose)
405 error (0, errno, _("Can't stat %s"), entry->path);
406 free (entry->path);
407 free (entry);
408 }
409 else
410 {
411 entry->ino = stat_buf.st_ino;
412 entry->dev = stat_buf.st_dev;
413
414 if (add_single_dir (entry, 1))
415 /* Add glibc-hwcaps subdirectories if present. */
416 add_glibc_hwcaps_subdirectories (entry, path);
417 }
418
419 if (opt_chroot != NULL)
420 free (path);
421 }
422
423 static void
424 add_dir (const char *line)
425 {
426 add_dir_1 (line, "<builtin>", 0);
427 }
428
429 static int
430 chroot_stat (const char *real_path, const char *path, struct stat *st)
431 {
432 int ret;
433 char *canon_path;
434
435 if (!opt_chroot)
436 return stat (real_path, st);
437
438 ret = lstat (real_path, st);
439 if (ret || !S_ISLNK (st->st_mode))
440 return ret;
441
442 canon_path = chroot_canon (opt_chroot, path);
443 if (canon_path == NULL)
444 return -1;
445
446 ret = stat (canon_path, st);
447 free (canon_path);
448 return ret;
449 }
450
451 /* Create a symbolic link from soname to libname in directory path. */
452 static void
453 create_links (const char *real_path, const char *path, const char *libname,
454 const char *soname)
455 {
456 char *full_libname, *full_soname;
457 char *real_full_libname, *real_full_soname;
458 struct stat stat_lib, stat_so, lstat_so;
459 int do_link = 1;
460 int do_remove = 1;
461 /* XXX: The logics in this function should be simplified. */
462
463 /* Get complete path. */
464 full_libname = alloca (strlen (path) + strlen (libname) + 2);
465 full_soname = alloca (strlen (path) + strlen (soname) + 2);
466 sprintf (full_libname, "%s/%s", path, libname);
467 sprintf (full_soname, "%s/%s", path, soname);
468 if (opt_chroot != NULL)
469 {
470 real_full_libname = alloca (strlen (real_path) + strlen (libname) + 2);
471 real_full_soname = alloca (strlen (real_path) + strlen (soname) + 2);
472 sprintf (real_full_libname, "%s/%s", real_path, libname);
473 sprintf (real_full_soname, "%s/%s", real_path, soname);
474 }
475 else
476 {
477 real_full_libname = full_libname;
478 real_full_soname = full_soname;
479 }
480
481 /* Does soname already exist and point to the right library? */
482 if (chroot_stat (real_full_soname, full_soname, &stat_so) == 0)
483 {
484 if (chroot_stat (real_full_libname, full_libname, &stat_lib))
485 {
486 error (0, 0, _("Can't stat %s\n"), full_libname);
487 return;
488 }
489 if (stat_lib.st_dev == stat_so.st_dev
490 && stat_lib.st_ino == stat_so.st_ino)
491 /* Link is already correct. */
492 do_link = 0;
493 else if (lstat (full_soname, &lstat_so) == 0
494 && !S_ISLNK (lstat_so.st_mode))
495 {
496 error (0, 0, _("%s is not a symbolic link\n"), full_soname);
497 do_link = 0;
498 do_remove = 0;
499 }
500 }
501 else if (lstat (real_full_soname, &lstat_so) != 0
502 || !S_ISLNK (lstat_so.st_mode))
503 /* Unless it is a stale symlink, there is no need to remove. */
504 do_remove = 0;
505
506 if (opt_verbose)
507 printf ("\t%s -> %s", soname, libname);
508
509 if (do_link && opt_link)
510 {
511 /* Remove old link. */
512 if (do_remove)
513 if (unlink (real_full_soname))
514 {
515 error (0, 0, _("Can't unlink %s"), full_soname);
516 do_link = 0;
517 }
518 /* Create symbolic link. */
519 if (do_link && symlink (libname, real_full_soname))
520 {
521 error (0, 0, _("Can't link %s to %s"), full_soname, libname);
522 do_link = 0;
523 }
524 if (opt_verbose)
525 {
526 if (do_link)
527 fputs (_(" (changed)\n"), stdout);
528 else
529 fputs (_(" (SKIPPED)\n"), stdout);
530 }
531 }
532 else if (opt_verbose)
533 fputs ("\n", stdout);
534 }
535
536 /* Manually link the given library. */
537 static void
538 manual_link (char *library)
539 {
540 char *path;
541 char *real_path;
542 char *real_library;
543 char *libname;
544 char *soname;
545 struct stat stat_buf;
546 int flag;
547 unsigned int isa_level;
548
549 /* Prepare arguments for create_links call. Split library name in
550 directory and filename first. Since path is allocated, we've got
551 to be careful to free at the end. */
552 path = xstrdup (library);
553 libname = strrchr (path, '/');
554
555 if (libname)
556 {
557 /* Successfully split names. Check if path is just "/" to avoid
558 an empty path. */
559 if (libname == path)
560 {
561 libname = library + 1;
562 path = xrealloc (path, 2);
563 strcpy (path, "/");
564 }
565 else
566 {
567 *libname = '\0';
568 ++libname;
569 }
570 }
571 else
572 {
573 /* There's no path, construct one. */
574 libname = library;
575 path = xrealloc (path, 2);
576 strcpy (path, ".");
577 }
578
579 if (opt_chroot != NULL)
580 {
581 real_path = chroot_canon (opt_chroot, path);
582 if (real_path == NULL)
583 {
584 error (0, errno, _("Can't find %s"), path);
585 free (path);
586 return;
587 }
588 real_library = alloca (strlen (real_path) + strlen (libname) + 2);
589 sprintf (real_library, "%s/%s", real_path, libname);
590 }
591 else
592 {
593 real_path = path;
594 real_library = library;
595 }
596
597 /* Do some sanity checks first. */
598 if (lstat (real_library, &stat_buf))
599 {
600 error (0, errno, _("Cannot lstat %s"), library);
601 goto out;
602 }
603 /* We don't want links here! */
604 else if (!S_ISREG (stat_buf.st_mode))
605 {
606 error (0, 0, _("Ignored file %s since it is not a regular file."),
607 library);
608 goto out;
609 }
610
611 if (process_file (real_library, library, libname, &flag, &isa_level, &soname,
612 0, &stat_buf))
613 {
614 error (0, 0, _("No link created since soname could not be found for %s"),
615 library);
616 goto out;
617 }
618 if (soname == NULL)
619 soname = xstrdup (libname);
620 create_links (real_path, path, libname, soname);
621 free (soname);
622 out:
623 if (path != real_path)
624 free (real_path);
625 free (path);
626 }
627
628
629 /* Read a whole directory and search for libraries.
630 The purpose is two-fold:
631 - search for libraries which will be added to the cache
632 - create symbolic links to the soname for each library
633
634 This has to be done separately for each directory.
635
636 To keep track of which libraries to add to the cache and which
637 links to create, we save a list of all libraries.
638
639 The algorithm is basically:
640 for all libraries in the directory do
641 get soname of library
642 if soname is already in list
643 if new library is newer, replace entry
644 otherwise ignore this library
645 otherwise add library to list
646
647 For example, if the two libraries libxy.so.1.1 and libxy.so.1.2
648 exist and both have the same soname, e.g. libxy.so, a symbolic link
649 is created from libxy.so.1.2 (the newer one) to libxy.so.
650 libxy.so.1.2 and libxy.so are added to the cache - but not
651 libxy.so.1.1. */
652
653 /* Information for one library. */
654 struct dlib_entry
655 {
656 char *name;
657 char *soname;
658 int flag;
659 int is_link;
660 unsigned int isa_level;
661 struct dlib_entry *next;
662 };
663
664
665 static void
666 search_dir (const struct dir_entry *entry)
667 {
668 if (opt_verbose)
669 {
670 if (entry->hwcaps == NULL)
671 printf ("%s:", entry->path);
672 else
673 printf ("%s: (hwcap: \"%s\")", entry->path,
674 glibc_hwcaps_subdirectory_name (entry->hwcaps));
675 printf (_(" (from %s:%d)\n"), entry->from_file, entry->from_line);
676 }
677
678 char *dir_name;
679 char *real_file_name;
680 char *file_name;
681 if (opt_chroot != NULL)
682 dir_name = chroot_canon (opt_chroot, entry->path);
683 else
684 dir_name = entry->path;
685
686 DIR *dir;
687 if (dir_name == NULL || (dir = opendir (dir_name)) == NULL)
688 {
689 if (opt_verbose)
690 error (0, errno, _("Can't open directory %s"), entry->path);
691 if (opt_chroot != NULL)
692 free (dir_name);
693 return;
694 }
695
696 struct dirent64 *direntry;
697 struct dlib_entry *dlibs = NULL;
698 while ((direntry = readdir64 (dir)) != NULL)
699 {
700 int flag;
701 /* We only look at links and regular files. */
702 if (direntry->d_type != DT_UNKNOWN
703 && direntry->d_type != DT_LNK
704 && direntry->d_type != DT_REG
705 && direntry->d_type != DT_DIR)
706 continue;
707 /* Does this file look like a shared library? The dynamic linker
708 is also considered as shared library. */
709 if (!_dl_is_dso (direntry->d_name)
710 && (direntry->d_type == DT_REG || entry->hwcaps == NULL))
711 continue;
712
713 size_t len = strlen (direntry->d_name);
714 /* Skip temporary files created by the prelink program. Files with
715 names like these are never really DSOs we want to look at. */
716 if (len >= sizeof (".#prelink#") - 1)
717 {
718 if (strcmp (direntry->d_name + len - sizeof (".#prelink#") + 1,
719 ".#prelink#") == 0)
720 continue;
721 if (len >= sizeof (".#prelink#.XXXXXX") - 1
722 && memcmp (direntry->d_name + len - sizeof (".#prelink#.XXXXXX")
723 + 1, ".#prelink#.", sizeof (".#prelink#.") - 1) == 0)
724 continue;
725 }
726 if (asprintf (&file_name, "%s/%s", entry->path, direntry->d_name) < 0)
727 error (EXIT_FAILURE, errno, _("Could not form library path"));
728 if (opt_chroot != NULL)
729 {
730 if (asprintf (&real_file_name, "%s/%s",
731 dir_name, direntry->d_name) < 0)
732 error (EXIT_FAILURE, errno, _("Could not form library path"));
733 }
734 else
735 real_file_name = xstrdup (file_name);
736
737 struct stat lstat_buf;
738 /* We optimize and try to do the lstat call only if needed. */
739 if (direntry->d_type != DT_UNKNOWN)
740 lstat_buf.st_mode = DTTOIF (direntry->d_type);
741 else
742 if (__glibc_unlikely (lstat (real_file_name, &lstat_buf)))
743 {
744 error (0, errno, _("Cannot lstat %s"), file_name);
745 goto next;
746 }
747
748 struct stat stat_buf;
749 int is_link = S_ISLNK (lstat_buf.st_mode);
750 if (is_link)
751 {
752 /* In case of symlink, we check if the symlink refers to
753 a directory. */
754 char *target_name = real_file_name;
755 if (opt_chroot != NULL)
756 {
757 target_name = chroot_canon (opt_chroot, file_name);
758 if (target_name == NULL)
759 {
760 if (strstr (file_name, ".so") == NULL)
761 error (0, 0, _("Input file %s not found.\n"), file_name);
762 goto next;
763 }
764 }
765 if (__glibc_unlikely (stat (target_name, &stat_buf)))
766 {
767 if (opt_verbose)
768 error (0, errno, _("Cannot stat %s"), file_name);
769
770 /* Remove stale symlinks. */
771 if (opt_link && strstr (direntry->d_name, ".so."))
772 unlink (real_file_name);
773
774 if (opt_chroot != NULL)
775 free (target_name);
776
777 goto next;
778 }
779
780 if (opt_chroot != NULL)
781 free (target_name);
782
783 /* lstat_buf is later stored, update contents. */
784 lstat_buf.st_dev = stat_buf.st_dev;
785 lstat_buf.st_ino = stat_buf.st_ino;
786 lstat_buf.st_size = stat_buf.st_size;
787 lstat_buf.st_ctime = stat_buf.st_ctime;
788 }
789 else if (!S_ISREG (lstat_buf.st_mode))
790 goto next;
791
792 char *real_name;
793 if (opt_chroot != NULL && is_link)
794 {
795 real_name = chroot_canon (opt_chroot, file_name);
796 if (real_name == NULL)
797 {
798 if (strstr (file_name, ".so") == NULL)
799 error (0, 0, _("Input file %s not found.\n"), file_name);
800 goto next;
801 }
802 }
803 else
804 real_name = real_file_name;
805
806 /* Call lstat if not done yet. */
807 if (!is_link
808 && direntry->d_type != DT_UNKNOWN
809 && __builtin_expect (lstat (real_file_name, &lstat_buf), 0))
810 {
811 error (0, errno, _("Cannot lstat %s"), file_name);
812 goto next;
813 }
814
815 /* First search whether the auxiliary cache contains this
816 library already and it's not changed. */
817 char *soname;
818 unsigned int isa_level;
819 if (!search_aux_cache (&lstat_buf, &flag, &isa_level, &soname))
820 {
821 if (process_file (real_name, file_name, direntry->d_name, &flag,
822 &isa_level, &soname, is_link, &lstat_buf))
823 {
824 if (real_name != real_file_name)
825 free (real_name);
826 goto next;
827 }
828 else if (opt_build_cache)
829 add_to_aux_cache (&lstat_buf, flag, isa_level, soname);
830 }
831
832 if (soname == NULL)
833 soname = xstrdup (direntry->d_name);
834
835 /* A link may just point to itself. */
836 if (is_link)
837 {
838 /* If the path the link points to isn't its soname or it is not
839 the .so symlink for ld(1), we treat it as a normal file.
840
841 You should always do this:
842
843 libfoo.so -> SONAME -> Arbitrary package-chosen name.
844
845 e.g. libfoo.so -> libfoo.so.1 -> libfooimp.so.9.99.
846 Given a SONAME of libfoo.so.1.
847
848 You should *never* do this:
849
850 libfoo.so -> libfooimp.so.9.99
851
852 If you do, and your SONAME is libfoo.so.1, then libfoo.so
853 fails to point at the SONAME. In that case ldconfig may consider
854 libfoo.so as another implementation of SONAME and will create
855 symlinks against it causing problems when you try to upgrade
856 or downgrade. The problems will arise because ldconfig will,
857 depending on directory ordering, creat symlinks against libfoo.so
858 e.g. libfoo.so.1.2 -> libfoo.so, but when libfoo.so is removed
859 (typically by the removal of a development package not required
860 for the runtime) it will break the libfoo.so.1.2 symlink and the
861 application will fail to start. */
862 const char *real_base_name = basename (real_file_name);
863
864 if (strcmp (real_base_name, soname) != 0)
865 {
866 len = strlen (real_base_name);
867 if (len < strlen (".so")
868 || strcmp (real_base_name + len - strlen (".so"), ".so") != 0
869 || strncmp (real_base_name, soname, len) != 0)
870 is_link = 0;
871 }
872 }
873
874 if (real_name != real_file_name)
875 free (real_name);
876
877 if (is_link)
878 {
879 free (soname);
880 soname = xstrdup (direntry->d_name);
881 }
882
883 /* Some sanity checks to print warnings. */
884 if (opt_verbose)
885 {
886 if (flag == FLAG_ELF_LIBC6 && entry->flag != FLAG_ELF_LIBC6)
887 error (0, 0, _("libc6 library %s in wrong directory"), file_name);
888 }
889
890 /* Add library to list. */
891 struct dlib_entry *dlib_ptr;
892 for (dlib_ptr = dlibs; dlib_ptr != NULL; dlib_ptr = dlib_ptr->next)
893 {
894 /* Is soname already in list? */
895 if (strcmp (dlib_ptr->soname, soname) == 0)
896 {
897 /* Prefer a file to a link, otherwise check which one
898 is newer. */
899 if ((!is_link && dlib_ptr->is_link)
900 || (is_link == dlib_ptr->is_link
901 && _dl_cache_libcmp (dlib_ptr->name, direntry->d_name) < 0))
902 {
903 /* It's newer - add it. */
904 /* Flag should be the same - sanity check. */
905 if (dlib_ptr->flag != flag)
906 error (0, 0, _("libraries %s and %s in directory %s have same soname but different type."),
907 dlib_ptr->name, direntry->d_name, entry->path);
908 free (dlib_ptr->name);
909 dlib_ptr->name = xstrdup (direntry->d_name);
910 dlib_ptr->is_link = is_link;
911 dlib_ptr->isa_level = isa_level;
912 }
913 /* Don't add this library, abort loop. */
914 /* Also free soname, since it's dynamically allocated. */
915 free (soname);
916 break;
917 }
918 }
919 /* Add the library if it's not already in. */
920 if (dlib_ptr == NULL)
921 {
922 dlib_ptr = (struct dlib_entry *)xmalloc (sizeof (struct dlib_entry));
923 dlib_ptr->name = xstrdup (direntry->d_name);
924 dlib_ptr->soname = soname;
925 dlib_ptr->flag = flag;
926 dlib_ptr->is_link = is_link;
927 dlib_ptr->isa_level = isa_level;
928 /* Add at head of list. */
929 dlib_ptr->next = dlibs;
930 dlibs = dlib_ptr;
931 }
932
933 next:
934 free (file_name);
935 free (real_file_name);
936 }
937
938 closedir (dir);
939
940 /* Now dlibs contains a list of all libs - add those to the cache
941 and created all symbolic links. */
942 struct dlib_entry *dlib_ptr;
943 for (dlib_ptr = dlibs; dlib_ptr != NULL; dlib_ptr = dlib_ptr->next)
944 {
945 /* The cached file name is the soname for non-glibc-hwcaps
946 subdirectories (relying on symbolic links; this helps with
947 library updates that change the file name), and the actual
948 file for glibc-hwcaps subdirectories. */
949 const char *filename;
950 if (entry->hwcaps == NULL)
951 {
952 /* Don't create links to links. */
953 if (dlib_ptr->is_link == 0)
954 create_links (dir_name, entry->path, dlib_ptr->name,
955 dlib_ptr->soname);
956 filename = dlib_ptr->soname;
957 }
958 else
959 {
960 /* Do not create links in glibc-hwcaps subdirectories, but
961 still log the cache addition. */
962 if (opt_verbose)
963 printf ("\t%s -> %s\n", dlib_ptr->soname, dlib_ptr->name);
964 filename = dlib_ptr->name;
965 }
966 if (opt_build_cache)
967 add_to_cache (entry->path, filename, dlib_ptr->soname,
968 dlib_ptr->flag, dlib_ptr->isa_level, entry->hwcaps);
969 }
970
971 /* Free all resources. */
972 while (dlibs)
973 {
974 dlib_ptr = dlibs;
975 free (dlib_ptr->soname);
976 free (dlib_ptr->name);
977 dlibs = dlibs->next;
978 free (dlib_ptr);
979 }
980
981 if (opt_chroot != NULL && dir_name != NULL)
982 free (dir_name);
983 }
984
985 /* Search through all libraries. */
986 static void
987 search_dirs (void)
988 {
989 struct dir_entry *entry;
990
991 for (entry = dir_entries; entry != NULL; entry = entry->next)
992 search_dir (entry);
993
994 /* Free all allocated memory. */
995 while (dir_entries)
996 {
997 entry = dir_entries;
998 dir_entries = dir_entries->next;
999 free (entry->path);
1000 free (entry);
1001 }
1002 }
1003
1004
1005 static void parse_conf_include (const char *config_file, unsigned int lineno,
1006 bool do_chroot, const char *pattern);
1007
1008 /* Parse configuration file. */
1009 static void
1010 parse_conf (const char *filename, bool do_chroot)
1011 {
1012 FILE *file = NULL;
1013 char *line = NULL;
1014 const char *canon;
1015 size_t len = 0;
1016 unsigned int lineno;
1017
1018 if (do_chroot && opt_chroot)
1019 {
1020 canon = chroot_canon (opt_chroot, filename);
1021 if (canon)
1022 file = fopen (canon, "r");
1023 else
1024 canon = filename;
1025 }
1026 else
1027 {
1028 canon = filename;
1029 file = fopen (filename, "r");
1030 }
1031
1032 if (file == NULL)
1033 {
1034 if (errno != ENOENT)
1035 error (0, errno, _("\
1036 Warning: ignoring configuration file that cannot be opened: %s"),
1037 canon);
1038 if (canon != filename)
1039 free ((char *) canon);
1040 return;
1041 }
1042
1043 /* No threads use this stream. */
1044 __fsetlocking (file, FSETLOCKING_BYCALLER);
1045
1046 if (canon != filename)
1047 free ((char *) canon);
1048
1049 lineno = 0;
1050 do
1051 {
1052 ssize_t n = getline (&line, &len, file);
1053 if (n < 0)
1054 break;
1055
1056 ++lineno;
1057 if (line[n - 1] == '\n')
1058 line[n - 1] = '\0';
1059
1060 /* Because the file format does not know any form of quoting we
1061 can search forward for the next '#' character and if found
1062 make it terminating the line. */
1063 *strchrnul (line, '#') = '\0';
1064
1065 /* Remove leading whitespace. NUL is no whitespace character. */
1066 char *cp = line;
1067 while (isspace (*cp))
1068 ++cp;
1069
1070 /* If the line is blank it is ignored. */
1071 if (cp[0] == '\0')
1072 continue;
1073
1074 if (!strncmp (cp, "include", 7) && isblank (cp[7]))
1075 {
1076 char *dir;
1077 cp += 8;
1078 while ((dir = strsep (&cp, " \t")) != NULL)
1079 if (dir[0] != '\0')
1080 parse_conf_include (filename, lineno, do_chroot, dir);
1081 }
1082 else if (!strncasecmp (cp, "hwcap", 5) && isblank (cp[5]))
1083 error (0, 0, _("%s:%u: hwcap directive ignored"), filename, lineno);
1084 else
1085 add_dir_1 (cp, filename, lineno);
1086 }
1087 while (!feof_unlocked (file));
1088
1089 /* Free buffer and close file. */
1090 free (line);
1091 fclose (file);
1092 }
1093
1094 /* Handle one word in an `include' line, a glob pattern of additional
1095 config files to read. */
1096 static void
1097 parse_conf_include (const char *config_file, unsigned int lineno,
1098 bool do_chroot, const char *pattern)
1099 {
1100 if (opt_chroot != NULL && pattern[0] != '/')
1101 error (EXIT_FAILURE, 0,
1102 _("need absolute file name for configuration file when using -r"));
1103
1104 char *copy = NULL;
1105 if (pattern[0] != '/' && strchr (config_file, '/') != NULL)
1106 {
1107 if (asprintf (&copy, "%s/%s", dirname (strdupa (config_file)),
1108 pattern) < 0)
1109 error (EXIT_FAILURE, 0, _("memory exhausted"));
1110 pattern = copy;
1111 }
1112
1113 glob64_t gl;
1114 int result;
1115 if (do_chroot && opt_chroot)
1116 {
1117 char *canon = chroot_canon (opt_chroot, pattern);
1118 if (canon == NULL)
1119 return;
1120 result = glob64 (canon, 0, NULL, &gl);
1121 free (canon);
1122 }
1123 else
1124 result = glob64 (pattern, 0, NULL, &gl);
1125
1126 switch (result)
1127 {
1128 case 0:
1129 for (size_t i = 0; i < gl.gl_pathc; ++i)
1130 parse_conf (gl.gl_pathv[i], false);
1131 globfree64 (&gl);
1132 break;
1133
1134 case GLOB_NOMATCH:
1135 break;
1136
1137 case GLOB_NOSPACE:
1138 errno = ENOMEM;
1139 /* Fall through. */
1140 case GLOB_ABORTED:
1141 if (opt_verbose)
1142 error (0, errno, _("%s:%u: cannot read directory %s"),
1143 config_file, lineno, pattern);
1144 break;
1145
1146 default:
1147 abort ();
1148 break;
1149 }
1150
1151 free (copy);
1152 }
1153
1154
1155 int
1156 main (int argc, char **argv)
1157 {
1158 /* Set locale via LC_ALL. */
1159 setlocale (LC_ALL, "");
1160
1161 /* But keep the C collation. That way `include' directives using
1162 globbing patterns are processed in a locale-independent order. */
1163 setlocale (LC_COLLATE, "C");
1164
1165 /* Set the text message domain. */
1166 textdomain (_libc_intl_domainname);
1167
1168 /* Parse and process arguments. */
1169 int remaining;
1170 argp_parse (&argp, argc, argv, 0, &remaining, NULL);
1171
1172 /* Remaining arguments are additional directories if opt_manual_link
1173 is not set. */
1174 if (remaining != argc && !opt_manual_link)
1175 {
1176 int i;
1177 for (i = remaining; i < argc; ++i)
1178 if (opt_build_cache && argv[i][0] != '/')
1179 error (EXIT_FAILURE, 0,
1180 _("relative path `%s' used to build cache"),
1181 argv[i]);
1182 else
1183 add_dir_1 (argv[i], "<cmdline>", 0);
1184 }
1185
1186 if (opt_chroot != NULL)
1187 {
1188 /* Normalize the path a bit, we might need it for printing later. */
1189 char *endp = strchr (opt_chroot, '\0');
1190 while (endp > opt_chroot && endp[-1] == '/')
1191 --endp;
1192 *endp = '\0';
1193 if (endp == opt_chroot)
1194 opt_chroot = NULL;
1195
1196 if (opt_chroot != NULL)
1197 {
1198 /* It is faster to use chroot if we can. */
1199 if (!chroot (opt_chroot))
1200 {
1201 if (chdir ("/"))
1202 error (EXIT_FAILURE, errno, _("Can't chdir to /"));
1203 opt_chroot = NULL;
1204 }
1205 }
1206 }
1207
1208 if (cache_file == NULL)
1209 {
1210 cache_file = alloca (strlen (LD_SO_CACHE) + 1);
1211 strcpy (cache_file, LD_SO_CACHE);
1212 }
1213
1214 if (config_file == NULL)
1215 config_file = LD_SO_CONF;
1216
1217 if (opt_print_cache)
1218 {
1219 if (opt_chroot != NULL)
1220 {
1221 char *p = chroot_canon (opt_chroot, cache_file);
1222 if (p == NULL)
1223 error (EXIT_FAILURE, errno, _("Can't open cache file %s\n"),
1224 cache_file);
1225 cache_file = p;
1226 }
1227 print_cache (cache_file);
1228 if (opt_chroot != NULL)
1229 free (cache_file);
1230 exit (0);
1231 }
1232
1233 if (opt_chroot != NULL)
1234 {
1235 /* Canonicalize the directory name of cache_file, not cache_file,
1236 because we'll rename a temporary cache file to it. */
1237 char *p = strrchr (cache_file, '/');
1238 char *canon = chroot_canon (opt_chroot,
1239 p ? (*p = '\0', cache_file) : "/");
1240
1241 if (canon == NULL)
1242 error (EXIT_FAILURE, errno,
1243 _("Can't open cache file directory %s\n"),
1244 p ? cache_file : "/");
1245
1246 if (p)
1247 ++p;
1248 else
1249 p = cache_file;
1250
1251 cache_file = alloca (strlen (canon) + strlen (p) + 2);
1252 sprintf (cache_file, "%s/%s", canon, p);
1253 free (canon);
1254 }
1255
1256 if (opt_manual_link)
1257 {
1258 /* Link all given libraries manually. */
1259 int i;
1260
1261 for (i = remaining; i < argc; ++i)
1262 manual_link (argv[i]);
1263
1264 exit (0);
1265 }
1266
1267
1268 if (opt_build_cache)
1269 init_cache ();
1270
1271 if (!opt_only_cline)
1272 {
1273 parse_conf (config_file, true);
1274
1275 /* Always add the standard search paths. */
1276 add_system_dir (SLIBDIR);
1277 if (strcmp (SLIBDIR, LIBDIR))
1278 add_system_dir (LIBDIR);
1279 }
1280
1281 const char *aux_cache_file = _PATH_LDCONFIG_AUX_CACHE;
1282 if (opt_chroot != NULL)
1283 aux_cache_file = chroot_canon (opt_chroot, aux_cache_file);
1284
1285 if (! opt_ignore_aux_cache && aux_cache_file)
1286 load_aux_cache (aux_cache_file);
1287 else
1288 init_aux_cache ();
1289
1290 search_dirs ();
1291
1292 if (opt_build_cache)
1293 {
1294 save_cache (cache_file);
1295 if (aux_cache_file)
1296 save_aux_cache (aux_cache_file);
1297 }
1298
1299 return 0;
1300 }