Provided by: manpages-ru-dev_4.18.1-1_all bug

ИМЯ

       dlinfo - возвращает информацию о динамически загруженном объекте

LIBRARY

       Dynamic linking library (libdl, -ldl)

СИНТАКСИС

       #define _GNU_SOURCE
       #include <link.h>
       #include <dlfcn.h>

       int dlinfo(void *restrict handle, int request, void *restrict info);

ОПИСАНИЕ

       Функция  dlinfo()  возвращает  информацию  о  динамически  загруженном объекте, на который
       указывает handle (обычно полученный ранее вызовом dlopen(3) или dlmopen(3)).  В  аргументе
       request  указывается  какую  информацию нужно получить. Аргумент info — указатель на буфер
       для хранения информации, возвращаемой вызовом; тип данного аргумента зависит от request.

       Для  request  поддерживаются  следующие  значения  (соответствующий  тип  info  показан  в
       скобках):

       RTLD_DI_LMID (Lmid_t *)
              Возвратить  ID  списка  карты  связи  (link-map list, пространство имён), в который
              загружен handle.

       RTLD_DI_LINKMAP (struct link_map **)
              Возвратить указатель на структуру link_map, соответствующую handle.  Аргумент  info
              указывает  на  указатель  на  структуру link_map, определённую в <link.h> следующим
              образом:

                  struct link_map {
                      ElfW(Addr) l_addr;  /* разница между
                                             адресом в файле ELF и
                                             адресом в памяти */
                      char      *l_name;  /* абсолютный путь, где
                                             был найден объект */
                      ElfW(Dyn) *l_ld;    /* динамический раздел
                                             общего объекта */
                      struct link_map *l_next, *l_prev;
                                          /* цепочка загруженных объектов */

                      /* дополнительные поля, зависящие от
                         реализации */
                  };

       RTLD_DI_ORIGIN (char *)
              Скопировать  путь  источника  общего  объекта  соответствующего  handle  в   место,
              указанное info.

       RTLD_DI_SERINFO (Dl_serinfo *)
              Возвратить  пути  поиска  библиотек  общего  объекта,  на который указывает handle.
              Аргумент info — указатель на Dl_serinfo с путями поиска. Так как  количество  путей
              поиска  может  быть  разным,  то размер структуры, на которую указывает info, может
              быть различным. Запрос RTLD_DI_SERINFOSIZE, описанный далее,  позволяет  приложению
              установить подходящий размер. Вызывающий должен выполнить следующие шаги:

              (1)  Использовать  запрос  RTLD_DI_SERINFOSIZE  для заполнения структуры Dl_serinfo
                   размером  (dls_size)   структуры,   необходимой   для   последующего   запроса
                   RTLD_DI_SERINFO.

              (2)  Выделить буфер Dl_serinfo правильного размера (dls_size).

              (3)  Использовать  запрос  RTLD_DI_SERINFOSIZE  для  заполнения  полей  dls_size  и
                   dls_cnt буфера, выделенного на предыдущем шаге.

              (4)  Использовать RTLD_DI_SERINFO для получения путей поиска библиотек.

              Структура Dl_serinfo определена следующим образом:

                  typedef struct {
                      size_t dls_size;           /* Size in bytes of
                                                    the whole buffer */
                      unsigned int dls_cnt;      /* Number of elements
                                                    in 'dls_serpath' */
                      Dl_serpath dls_serpath[1]; /* Actually longer,
                                                    'dls_cnt' elements */
                  } Dl_serinfo;

              Каждый из элементов dls_serpath, в упомянутой выше  структуре,  представляет  собой
              структуру следующего вида:

                  typedef struct {
                      char *dls_name;            /* имя каталога в
                                                     путях поиска библиотек */
                      unsigned int dls_flags;    /* показывает, откуда
                                                    возник каталог */
                  } Dl_serpath;

              Поле dls_flags в настоящее время не используется и всегда равно нулю.

       RTLD_DI_SERINFOSIZE (Dl_serinfo *)
              Заполнить  поля dls_size и dls_cnt структуры Dl_serinfo, на которую указывает info,
              значениями, подходящими  для  выделения  буфера,  который  будет  использоваться  в
              последующем запросе RTLD_DI_SERINFO.

       RTLD_DI_TLS_MODID (size_t *, начиная с glibc 2.4)
              Получить  ID модуля сегмента TLS (локальное хранилище нити) общего объекта, которое
              используется в перемещениях TLS. Если этот объект не задаёт сегмент TLS, то в *info
              помещается ноль.

       RTLD_DI_TLS_DATA (void **, начиная с glibc 2.4)
              Получить  указатель на блок TLS вызывающей нити, соответствующий этому сегменту TLS
              общего объекта. Если этот объект не задаёт сегмент PT_TLS, или  если  у  вызывающей
              нити для этого не выделен блок, то в *info помещается NULL.

ВОЗВРАЩАЕМОЕ ЗНАЧЕНИЕ

       При  успешном выполнении dlinfo() возвращает 0. При ошибке возвращается -1; причину ошибки
       можно узнать с помощью dlerror(3).

ВЕРСИИ

       Функция dlinfo() впервые появилась в glibc версии 2.3.3.

АТРИБУТЫ

       Описание терминов данного раздела смотрите в attributes(7).

       ┌───────────────────────────────────────────────────────┬──────────────────────┬──────────┐
       │ИнтерфейсАтрибутЗначение │
       ├───────────────────────────────────────────────────────┼──────────────────────┼──────────┤
       │dlinfo()                                               │ Безвредность в нитях │ MT-Safe  │
       └───────────────────────────────────────────────────────┴──────────────────────┴──────────┘

СТАНДАРТЫ

       Эта функция является нестандартным расширением GNU.

ЗАМЕЧАНИЯ

       Данная функция произошла от функции Solaris с тем же именем,  а  также  есть  в  некоторых
       других  системах.  Набор  запросов,  поддерживаемых различными реализациями, перекрывается
       лишь частично.

ПРИМЕРЫ

       Программа,  показанная  ниже,  открывает  общие  объекты  с  помощью  dlopen(3),  а  затем
       использует  запросы  RTLD_DI_SERINFOSIZE  и  RTLD_DI_SERINFO  для  получения библиотеки из
       списка путей поиска библиотек. Пример вывода работы программы:

           $ ./a.out /lib64/libm.so.6
           dls_serpath[0].dls_name = /lib64
           dls_serpath[1].dls_name = /usr/lib64

   Исходный код программы

       #define _GNU_SOURCE
       #include <dlfcn.h>
       #include <link.h>
       #include <stdio.h>
       #include <stdlib.h>

       int
       main(int argc, char *argv[])
       {
           void *handle;
           Dl_serinfo serinfo;
           Dl_serinfo *sip;

           if (argc != 2) {
               fprintf(stderr, "Использование: %s <libpath>\n", argv[0]);
               exit(EXIT_FAILURE);
           }

           /* Obtain a handle for shared object specified on command line. */

           handle = dlopen(argv[1], RTLD_NOW);
           if (handle == NULL) {
               fprintf(stderr, "ошибка dlopen(): %s\n", dlerror());
               exit(EXIT_FAILURE);
           }

           /* Discover the size of the buffer that we must pass to
              RTLD_DI_SERINFO. */

           if (dlinfo(handle, RTLD_DI_SERINFOSIZE, &serinfo) == -1) {
               fprintf(stderr, "ошибка RTLD_DI_SERINFOSIZE: %s\n", dlerror());
               exit(EXIT_FAILURE);
           }

           /* Allocate the buffer for use with RTLD_DI_SERINFO. */

           sip = malloc(serinfo.dls_size);
           if (sip == NULL) {
               perror("malloc");
               exit(EXIT_FAILURE);
           }

           /* Initialize the 'dls_size' and 'dls_cnt' fields in the newly
              allocated buffer. */

           if (dlinfo(handle, RTLD_DI_SERINFOSIZE, sip) == -1) {
               fprintf(stderr, "ошибка RTLD_DI_SERINFOSIZE: %s\n", dlerror());
               exit(EXIT_FAILURE);
           }

           /* Fetch and print library search list. */

           if (dlinfo(handle, RTLD_DI_SERINFO, sip) == -1) {
               fprintf(stderr, "ошибка RTLD_DI_SERINFO: %s\n", dlerror());
               exit(EXIT_FAILURE);
           }

           for (size_t j = 0; j < serinfo.dls_cnt; j++)
               printf("dls_serpath[%zu].dls_name = %s\n",
                      j, sip->dls_serpath[j].dls_name);

           exit(EXIT_SUCCESS);
       }

СМ. ТАКЖЕ

       dl_iterate_phdr(3), dladdr(3), dlerror(3), dlopen(3), dlsym(3), ld.so(8)

ПЕРЕВОД

       Русский перевод этой страницы руководства был сделан Yuri  Kozlov  <yuray@komyakino.ru>  и
       Иван Павлов <pavia00@gmail.com>

       Этот  перевод  является  бесплатной  документацией;  прочитайте  Стандартную  общественную
       лицензию GNU версии 3 ⟨https://www.gnu.org/licenses/gpl-3.0.html⟩ или более позднюю, чтобы
       узнать об условиях авторского права. Мы не несем НИКАКОЙ ОТВЕТСТВЕННОСТИ.

       Если  вы  обнаружите  ошибки  в  переводе этой страницы руководства, пожалуйста, отправьте
       электронное письмо на ⟨man-pages-ru-talks@lists.sourceforge.net⟩.