#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <dlfcn.h>
#include <dirent.h> // для работы с директориями
// Функция проверяет, оканчивается ли имя файла на .so
int is_so_file(const char *filename) {
const char *dot = strrchr(filename, '.');
return (dot && strcmp(dot, ".so") == 0);
}
int main(void) {
const char *dir_path = "."; // Сканируем текущую папку
DIR *dir = opendir(dir_path);
if (!dir) {
perror("Ошибка открытия директории");
return 1;
}
printf("=== Сканирование директории '%s' ===\n", dir_path);
struct dirent *entry;
// Читаем файлы в папке по очереди
while ((entry = readdir(dir)) != NULL) {
// Проверяем, что это обычный файл и он заканчивается на .so
if (entry->d_type == DT_REG && is_so_file(entry->d_name)) {
char full_path[256];
snprintf(full_path, sizeof(full_path), "./%s", entry->d_name);
printf("\nПробуем загрузить плагин: %s\n", entry->d_name);
// 1. Попытка загрузить библиотеку через dlopen
dlerror(); // Сброс предыдущих ошибок
void *handle = dlopen(full_path, RTLD_NOW);
char *error = dlerror();
if (!handle) {
printf("[ОШИБКА] Не удалось загрузить %s: %s\n", entry->d_name, error);
continue;
}
// 2. Поиск функции info
void (*info_func)(void) = dlsym(handle, "info");
error = dlerror();
if (error != NULL) {
// Если символ не найден — выводим предупреждение
printf("[ПРЕДУПРЕЖДЕНИЕ] В плагине %s отсутствует функция info()\n", entry->d_name);
} else {
// Если символ найден — вызываем функцию info()
printf("[УСПЕХ] Данные из плагина:\n");
info_func();
}
// 3. Выгружаем библиотеку
dlclose(handle);
}
}
closedir(dir);
printf("\n=== Обработка плагинов завершена ===\n");
return 0;
}