| Summary: | ocamlc can\'t compile a program with threads | ||||||
|---|---|---|---|---|---|---|---|
| Product: | Sisyphus | Reporter: | Sergey Vlasov <vsu> | ||||
| Component: | ocaml | Assignee: | Vitaly Lugovsky <vsl> | ||||
| Status: | CLOSED FIXED | QA Contact: | |||||
| Severity: | minor | ||||||
| Priority: | P4 | CC: | rider, shaba | ||||
| Version: | unstable | ||||||
| Hardware: | all | ||||||
| OS: | Linux | ||||||
| Attachments: |
|
||||||
0000844-ocaml-3.04+7-threadhack.patch - тот самый хакерский вариант с .weak 0000844-ocaml-3.04+7-threadhack.patch - тот самый хакерский вариант с .weak Лучше всего выбрать оба варианта - и не убивать байткодовые версии, и хакнуть posix.c Сейчас всё пересобираю (с CVS-ным 3.04+9)... Лучше всего выбрать оба варианта - и не убивать байткодовые версии, и хакнуть posix.c Сейчас всё пересобираю (с CVS-ным 3.04+9)... давно исправлено... |
ocamlc (на самом деле ocamlc.opt) не в состоянии скомпилировать в байт-код программу, использующую threads.cma. Простейший пример: ===== begin thrtest.ml ===== let _ = Thread.join (Thread.create (fun () -> print_string \"Hello\\n\") ()) ===== end thrtest.ml ===== $ rpm -q ocaml ocaml-3.04+7-alt1 $ ocamlopt -thread -o thrtest unix.cmxa threads.cmxa thrtest.ml $ ./thrtest Hello (так все работает) $ ocamlc -thread -o thrtest unix.cma threads.cma thrtest.ml Error on dynamically loaded library: /usr/lib/ocaml/dllthreads.so: undefined symbol: external_raise Причина подобной ситуации в том, что ocamlc при сборке байт-кода пытается подгрузить через dlopen() все указанные в *.cma-файлах динамические библиотеки (dll*.so), чтобы проверить наличие там нужных примитивов. Однако библиотека dllthreads.so ссылается на переменную external_raise, которая определена только в libcamlrun.a (и, соответственно, в /usr/bin/ocamlrun), но не в libasmrun.a. Поэтому dllthreads.so может быть загружена только программой, скомпилированной в байт-код. Видимые мной способы решения проблемы: 1. Проигнорировать и при необходимости собирать подобные программы с -custom - так собирается, но это некрасиво. 2. Вернуть на место байт-кодовый ocamlc (не заменять его полностью на ocamlc.opt). Для ocamlopt такой проблемы нет, поэтому его можно оставить полностью в native. 3. Всадить в otherlibs/systhreads/posix.c директиву: #ifndef NATIVE_CODE asm(\".weak external_raise\") #endif В результате dllthreads.so можно будет загрузить и из native-программы; работать она, естественно, не будет (при первой же попытке обращения к этой переменной получим SIGSEGV), но от нее это и не требуется - нужно лишь успешное выполнение dlopen() и dlsym(). (Попробовал собрать так - работает, lablgtktop_t собирается и по крайней мере выполняет свои же примеры (там потоки в явном виде не применяются - только свой при инициализации lablgtktop_t). Что будем делать? --- ---