У меня есть пакет R, над которым я работаю, который содержит код, написанный на C и C ++ в папке src. В настоящее время пакет компилируется и работает в Rstudio, так как он соответствует структуре каталогов по умолчанию. По мере сборки проекта я хочу иметь возможность организовать свой код в src, в подпапках. Следуя указаниям из раздела «Написание расширений R» — Компиляция в подкаталогах, я создал папку под названием «test» (/ src / test), которая теперь содержит все мои файлы (*. C, * .cpp, * .h) и модифицировал мой Макевар так —
SOURCES_C = $(wildcard test/*.c)
SOURCES_CPP = $(wildcard test/*.cpp)
PKG_CPPFLAGS= -I${R_HOME}/include -I.
PKG_LIBS = -L${R_HOME}/lib
CXX_STD = CXX11
OBJECTS =$(SOURCES_CPP:.cpp=.o) $(SOURCES_C:.c=.o)
all : $(SHLIB)
#PKG_CFLAGS= -Wall
clean : rm -f *.o
Я хочу иметь возможность компилировать программу в этом состоянии, где файлы C / C ++ находятся в подпапках внутри src. Используя вышеупомянутые Makevars ->, создаются отдельные объектные файлы из тестовой папки с правильными флагами и компилятором для всех файлов C / CPP. Однако есть некоторые расхождения с командой build для общего объекта. Это журнал при компиляции файлов в src / test, который завершается с неопределенной ошибкой символа.
gcc -std=gnu99 -shared -L/usr/local/lib64 -o BioCro.so test/BBox.o test/Climate.o test/Compound.o test/Grid.o test/LeafOptics.o test/Maths.o test/Normal.o test/Point3D.o test/Ray.o test/Triangle.o test/Vector3D.o test/runFastTracer.o test/Assigncropcent.o test/AuxBioCro.o test/AuxCropGro.o test/AuxMaizeGro.o test/AuxcaneGro.o test/Auxcropcent.o test/AuxwillowGro.o test/BioCro.o test/CalculateBiogeochem.o test/Calculate_Soil_Layer_Temperature.o test/CanA.o test/CanAC_3D.o test/Century.o test/Copy_CropCent_To_DayCent_Structure.o test/Copy_SoilWater_BioCro_To_CropCent.o test/CropGro.o test/CropGro_c.o test/Filling_BioCro_SoilStructure.o test/assignManagement.o test/c3CanA.o test/c3EvapoTrans.o test/c3photo.o test/c4photo.o test/caneGro.o test/createNULLc3tree.o test/cropcent.o test/dailywillow.o test/denitrify.o test/diffusiv.o test/eC4photo.o test/getIdirIdiff.o test/getsoilprop.o test/leachdly.o test/maizeGro.o test/methane.o test/microclimate_for_3Dcanopy.o test/nitrify.o test/nox_pulse.o test/pi_funcs.o test/printcropcentoutput.o test/test_mainC.o test/tgmodel.o test/tracegas.o test/update_3Dcanopy_structure.o test/wfps.o test/willowCent.o test/willowGro.o -L/usr/local/R-3.1.0/lib64/R/lib -L/usr/local/R-3.1.0/lib64/R/lib -lR
installing to /home/vashist1/R/x86_64-unknown-linux-gnu-library/3.1/BioCro/
** R
** data
** inst
** preparing package for lazy loading
** help
*** installing help indices
** building package indices
** installing vignettes
** testing if installed package can be loaded
Error in dyn.load(file, DLLpath = DLLpath, ...) :
unable to load shared object '/home/vashist1/R/x86_64-unknown-linux-gnu-library/3.1/BioCro/libs/BioCro.so':
/home/vashist1/R/x86_64-unknown-linux-gnu-library/3.1/BioCro/libs/BioCro.so:
undefined symbol: _ZTVN10__cxxabiv117__class_type_infoE
Error: loading failed
По сравнению с успешным журналом, который успешно строится!
g++ -shared -L/usr/local/lib64 -o BioCro.so Assigncropcent.o AuxBioCro.o AuxCropGro.o AuxMaizeGro.o AuxcaneGro.o Auxcropcent.o AuxwillowGro.o BBox.o BioCro.o CalculateBiogeochem.o Calculate_Soil_Layer_Temperature.o CanA.o CanAC_3D.o Century.o Climate.o Compound.o Copy_CropCent_To_DayCent_Structure.o Copy_SoilWater_BioCro_To_CropCent.o CropGro.o CropGro_c.o Filling_BioCro_SoilStructure.o Grid.o LeafOptics.o Maths.o Normal.o Point3D.o Ray.o Triangle.o Vector3D.o assignManagement.o c3CanA.o c3EvapoTrans.o c3photo.o c4photo.o caneGro.o createNULLc3tree.o cropcent.o dailywillow.o denitrify.o diffusiv.o eC4photo.o getIdirIdiff.o getsoilprop.o leachdly.o maizeGro.o methane.o microclimate_for_3Dcanopy.o nitrify.o nox_pulse.o pi_funcs.o printcropcentoutput.o runFastTracer.o test_mainC.o tgmodel.o tracegas.o update_3Dcanopy_structure.o wfps.o willowCent.o willowGro.o -L/usr/local/R-3.1.0/lib64/R/lib -lR
installing to /home/vashist1/R/x86_64-unknown-linux-gnu-library/3.1/BioCro/libs
1) Общий объект компилируется с использованием g ++ в условиях по умолчанию, тогда как в условиях подкаталогов используется компилятор gcc. Могу ли я изменить это поведение через Makevars?
2) Дальнейшие исследования позволили мне обнаружить, что неопределенная ошибка символа является ошибкой компоновки, исправляемой флагом -L / -l. Однако флаг -L одинаков для обеих команд сборки. Есть ли какая-либо другая библиотека, на которую я не могу установить ссылку, которая связана по умолчанию?
Я столкнулся с той же проблемой. Рассматривая пример пакета RSiena, упомянутого в качестве примера в «Написание расширений R» раздел 1.2.1.3 Я заметил, что этот пакет еще .cpp
файлы не в подкаталоге. Поэтому я добавил dummy.cpp
файл в src/
со следующим содержанием:
void dummy (void)
{
}
После этого g++
был правильно использован для шага связывания и .so
файл был создан, как и ожидалось.
В моем случае оказывается, что мне не нужно менять Makevars
файлы, как я впервые упомянул в своем ответе. Даже без изменений ниже (так что только имея dummy.cpp
файл присутствует в src/
) ссылки сделаны правильно.
Я оставлю это в случае, если это может помочь кому-то еще с (немного) другими настройками.
И добавить соответствующие .o
файл в списке $(OBJECTS)
переменная в Makevars
файл:
OBJECTS = $(SOURCES:.cpp=.o) dummy.o