До сих пор мы писали с Вами простые динамические библиотеки, поэтому у нас не болела голова об инициализации внутренних переменных. А представьте себе более сложную ситуацию, когда функции библиотеки для работы требуют правильно инициализированные переменные. Ну, например, для работы функции нужен буфер или массив.
Специально для таких случаев в библиотеках можно задавать инициализирующую и деинициализирующую функции:
· void _init() - инициализация
· void _fini() - деинициализация
Чтобы понять, что к чему, введем в нашей библиотеке lib.c переменную test и возвращающую ее функцию:
char *test; char *ret_test(){ return test;};
Пишем основную программу main.c. Она очень похожа на предыдущий наш проект, поэтому можете его модифицировать:
После компиляции всего этого хозяйства мы получим результат:
dron:~# gcc -c lib.c -fPICdron:~# gcc -shared lib.o -o libtest.sodron:~# gcc -o main main.c -ldldron:~# ./mainReturn of ret_test: "(null)" [(nil)]dron:~#
Как видите переменная test оказалась равной NULL, а нам бы хотелось нечто другое. Ну, так давайте посмотрим как работают функции _init() и _fini(). Создадим вторую библиотеку lib1.c:
dron:~# gcc -c lib1.c -fPICdron:~# gcc -shared lib1.o -o libtest.solib1.o: In function `_init':lib1.o(.text+0x24): multiple definition of `_init'/usr/lib/crti.o(.init+0x0): first defined herelib1.o: In function `_fini':lib1.o(.text+0xc0): multiple definition of `_fini'/usr/lib/crti.o(.fini+0x0): first defined herecollect2: ld returned 1 exit statusdron:~#
Опаньки... Облом. Что же это такое ?! Оказывается кто-то уже использовал эти функции до нас и программа не может слинковаться. После долгого копания в нескольких чужих исходниках я получил ответ на этот вопрос. Оказывается, чтобы избавиться от мешающей библиотеки надо использовать ключ компилятора -nostdlib. Попробуем:
Смотрите-ка, все прекрасно скомилировалось. Теперь попробуем запустить main:
dron:~# ./main_init() executed...Return of ret_test: "dron!" [0x8049c20]_fini() executed...dron:~#
Ну как ? Помоему классно. Теперь можно спокойно создавать для работы библиотеки правильно инициализированные переменные. Однако классные эти штуки - динамические библиотеки ! А Вы что хотели ? Тот же Windows только на своих DLL и живет. А Linux ничем не хуже...