提问人:aman 提问时间:8/30/2023 最后编辑:aman 更新时间:8/30/2023 访问量:47
Emscripten 和 Ceres-Solver 的链接问题:“未定义的符号:ceres::CostFunction 的 typeinfo”
Linking Issue with Emscripten and Ceres-Solver: "undefined symbol: typeinfo for ceres::CostFunction"
问:
我正在做一个使用 Ceres-Solver 库的项目。使用常规 CMake 设置时,项目编译成功。但是,当我尝试使用 Emscripten 编译器编译它时,我遇到了链接问题。
我得到的错误是:
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libamd.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libamd.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libblas.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libblas.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libbtf.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libbtf.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcamd.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcamd.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libccolamd.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libccolamd.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libceres.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libceres.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcholmod.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcholmod.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcolamd.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcolamd.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcxsparse.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libcxsparse.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libgflags.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libgflags.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libgpuqrengine.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libgpuqrengine.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspex.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspex.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspqr.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspqr.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libklu.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libklu.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libklu_cholmod.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libklu_cholmod.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libldl.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libldl.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libmongoose.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libmongoose.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/librbio.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/librbio.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspqr_cuda.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libspqr_cuda.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/liblapack.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/liblapack.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libsuitesparseconfig.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libsuitesparseconfig.a: adding index [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libumfpack.a: archive is missing an index; Use emar when creating libraries to ensure an index is created [-Wemcc]
em++: warning: /rnd_ceres-solver/thirdparty/build/install/lib/libumfpack.a: adding index [-Wemcc]
wasm-ld: error: CMakeFiles/simple_bundle_adjuster.dir/bundle_adjuster.cc.o: undefined symbol: typeinfo for ceres::CostFunction
另外,如何确保使用 emscripten 使档案是由 emar 而不是系统 ar 工具创建的?
重现步骤:
仅使用 emscripten 编译器从源代码构建 ceres-solver,所有依赖库也来自源代码。谷神星求解器安装
我现在正在尝试使用 Emscripten 和以下 shell 脚本构建它,该脚本设置 Emscripten 环境并执行和:
emcmake
make
#!/bin/bash echo "Setting up emsdk environment..." source ~/emsdk/emsdk_env.sh # Specify the directory where you want to create the build folder build_dir=build # Ensure we're in the same directory as the CMakeLists.txt file script_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")" >/dev/null 2>&1 && pwd)" # Create the build directory if it doesn't exist mkdir -p "${script_dir}/${build_dir}" # Navigate into the build directory cd "${script_dir}/${build_dir}" || { echo "ERROR: Failed to navigate into build directory. Exiting..."; exit 1; } echo "Running emcmake and make..." emcmake cmake .. ; time make
CMakeLists.txt:
cmake_minimum_required(VERSION 3.5)
project(simple_bundle_adjuster)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
add_definitions(-Wc++17-narrowing)
function(list_transform_prepend var prefix)
set(temp "")
foreach(f ${${var}})
list(APPEND temp "${prefix}${f}")
endforeach()
set(${var} "${temp}" PARENT_SCOPE)
endfunction()
# Set the path to local packages
list(APPEND CMAKE_PREFIX_PATH "${CMAKE_SOURCE_DIR}/thirdparty/build/install")
include_directories("${CMAKE_SOURCE_DIR}/thirdparty/build/install/include")
include_directories("${CMAKE_SOURCE_DIR}/thirdparty/build/install/share/eigen3/cmake")
include_directories("${CMAKE_SOURCE_DIR}/thirdparty/build/install/include/eigen3")
# Manually specify the directory of Eigen3
set(Eigen3_DIR "${CMAKE_SOURCE_DIR}/thirdparty/build/install/share/eigen3/cmake")
# find_package(Eigen3 REQUIRED PATHS "${CMAKE_SOURCE_DIR}/thirdparty/build/install/share/eigen3/cmake")
set(AMDL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libamd.a")
set(BLASL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libblas.a")
set(BTF "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libbtf.a")
set(CAMDL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libcamd.a")
set(CCOLAMDL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libccolamd.a")
set(CERESL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libceres.a")
set(CHOLMODL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libcholmod.a")
set(COLAMDL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libcolamd.a")
set(CXSPARSEL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libcxsparse.a")
set(GFLAGS "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libgflags.a")
# set(GLOG "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libglog.dylib")
set(GPUQRENGINEL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libgpuqrengine.a")
set(SPEXL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libspex.a")
set(SPQRL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libspqr.a")
set(KLUL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libklu.a")
set(KLU_CHOLMODL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libklu_cholmod.a")
set(LDL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libldl.a")
set(MONGOOSE "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libmongoose.a")
set(RBIOL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/librbio.a")
set(SPQR_CUDA "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libspqr_cuda.a")
set(LAPACKL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/liblapack.a")
set(SuiteSparse_DEPENDENCY "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libsuitesparseconfig.a")
set(UMFL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libumfpack.a")
set(CERESL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libceres.a")
# set(GRAPHBLASL "${CMAKE_SOURCE_DIR}/thirdparty/build/install/lib/libgraphblas.dylib")
# test
set(CERES_SOLVER_DEPENDENCIESL ${AMDL} ${BLASL} ${BTF} ${CAMDL} ${CCOLAMDL} ${CERESL} ${CHOLMODL} ${COLAMDL} ${CXSPARSEL} ${GFLAGS} ${GPUQRENGINEL} ${SPEXL} ${SPQRL} ${KLUL} ${KLU_CHOLMODL} ${LDL} ${MONGOOSE} ${RBIOL} ${SPQR_CUDA} ${LAPACKL} ${SuiteSparse_DEPENDENCY} ${UMFL} ${GRAPHBLASL})
list_transform_prepend(CERES_SOLVER_DEPENDENCIESL "")
# set(CERES_SOLVER ${CERES_SOLVER_DEPENDENCIESL})
# Add source files
add_executable(simple_bundle_adjuster bundle_adjuster.cc)
# Link the libraries
target_link_libraries(simple_bundle_adjuster ${CERES_SOLVER_DEPENDENCIESL})
这会导致链接错误。
- 我已经验证了链接过程中是否包含所有必要的库。
- 我怀疑我需要传递一些 Emscripten 编译器标志,但我不确定哪些标志可以解决此问题。
相关代码:.cc
#include "ceres/ceres.h"
int main() {
BALProblem bal_problem;
if (!bal_problem.LoadData()) {
std::cerr << "ERROR: unable to load data " << "\n";
return 1;
}
const double* observations = bal_problem.observations();
// Create residuals for each observation in the bundle adjustment problem. The
// parameters for cameras and points are added automatically.
ceres::Problem problem;
for (int i = 0; i < bal_problem.num_observations(); ++i) {
// Each Residual block takes a point and a camera as input and outputs a 2
// dimensional residual. Internally, the cost function stores the observed
// image location and compares the reprojection against the observation.
ceres::CostFunction* cost_function =
SnavelyReprojectionError::Create(observations[2 * i + 0],
observations[2 * i + 1]);
//ceres::LossFunction* loss_function = new ceres::TukeyLoss(10.0); // MAH Robust method
problem.AddResidualBlock(cost_function,
NULL /*squared loss */,
bal_problem.mutable_camera_for_observation(i),
bal_problem.mutable_point_for_observation(i));
}
}
我将不胜感激解决此问题的任何建议。谢谢。
答: 暂无答案
评论