Машина / система / компилятор: Surface Pro 3 / Ubuntu 16.04 64bit на VMWare / GCC 5.4.0
Мне нужно вызвать код OCaml из моего приложения Qt.
Я собрал OCaml 4.05 из исходников, следуя инструкциям в install.doc, но без компиляции компилятора нативного кода.
Теперь в Qt у меня есть следующий код:
.профессионал
QT += core gui
TARGET = Editor
TEMPLATE = app
unix:!macx: LIBS += -L$$PWD/../../../../../../../../../usr/local/lib/ocaml/ -lcamlrun
INCLUDEPATH += $$PWD/../../../../../../../../../usr/local/lib/ocaml
DEPENDPATH += $$PWD/../../../../../../../../../usr/local/lib/ocaml
unix:!macx: PRE_TARGETDEPS += $$PWD/../../../../../../../../../usr/local/lib/ocaml/libcamlrun.a
LIBS += -L$$PWD/../../../../../../../../../usr/lib/x86_64-linux-gnu/ -ldl
SOURCES += \
main.cpp \
mainwindow.cpp \
HEADERS += \
mainwindow.h \
FORMS += \
mainwindow.ui
RESOURCES += \
resources.qrc
mainwindow.h
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
extern "C" {
#include "caml/mlvalues.h"#include "caml/callback.h"}
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
...
};
#endif // MAINWINDOW_H
mainwindow.cpp
#include "mainwindow.h"
char* callCaml(int arg)
{
static value* closure = nullptr;
if (!closure)
closure = caml_named_value("fct");
return String_val( caml_callback(*closure, Val_int(arg)) );
}
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent)
,ui(new Ui::MainWindow)
{
ui->setupUi(this);
caml_main((char**)(&("a.o")));
msgBox.setText(callCaml(7));
msgBox.show();
}
Код OCaml
let fct = string_of_int;;
let () = Callback.register "fct" fct;;
Скомпилировано с командой
ocamlc -output-obj -o a.o caml.ml
это дает мне предупреждение:
a.c: In function ‘caml_startup_exn’:
a.c:2738:10: warning: implicit declaration of function
‘caml_startup_code_exn’ [-Wimplicit-function-declaration]
return caml_startup_code_exn(caml_code, sizeof(caml_code),
^
Теперь, когда я компилирую свой проект с помощью Qt, я получаю некоторые ошибки
/.../usr/local/lib/ocaml//libcamlrun.a(startup.o): In function `caml_main':
startup.c:(.text+0x6ab): undefined reference to `caml_names_of_builtin_cprim'
startup.c:(.text+0x6cf): undefined reference to `caml_names_of_builtin_cprim'
/.../usr/local/lib/ocaml//libcamlrun.a(dynlink.o): In function `caml_build_primitive_table':
dynlink.c:(.text+0x223): undefined reference to `caml_names_of_builtin_cprim'
dynlink.c:(.text+0x242): undefined reference to `caml_names_of_builtin_cprim'
dynlink.c:(.text+0x262): undefined reference to `caml_builtin_cprim'
/.../usr/local/lib/ocaml//libcamlrun.a(dynlink.o): In function `caml_build_primitive_table_builtin':
dynlink.c:(.text+0x3b3): undefined reference to `caml_builtin_cprim'
dynlink.c:(.text+0x3d4): undefined reference to `caml_builtin_cprim'
collect2: error: ld returned 1 exit status
Я уточняю, что я новичок в Linux и Qt.
Спасибо за помощь !
Я не уверен, что ты сделал не так. Хотя вряд ли, потому что вы не создали собственный компилятор, чего-то не хватает. В любом случае, используя ocaml, предоставленный ubuntu, я не могу воспроизвести вашу проблему.
Поэтому я предлагаю запустить «apt-get install ocaml» и использовать его для компиляции вашего источника.
Других решений пока нет …