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