diff --git a/include/small_gicp/ann/kdtree_omp.hpp b/include/small_gicp/ann/kdtree_omp.hpp index 89f7b2b..79bdcd8 100644 --- a/include/small_gicp/ann/kdtree_omp.hpp +++ b/include/small_gicp/ann/kdtree_omp.hpp @@ -5,6 +5,12 @@ #include #include +#ifdef _MSC_VER +#pragma message("warning: Task-based OpenMP parallelism causes run-time memory errors with Eigen matrices.") +#pragma message("warning: Thus, OpenMP-based multi-threading for KdTree construction is disabled on MSVC.") +#endif + + namespace small_gicp { /// @brief Kd-tree builder with OpenMP. @@ -23,14 +29,17 @@ struct KdTreeBuilderOMP { std::atomic_uint64_t node_count = 0; kdtree.nodes.resize(traits::size(points)); +#ifndef _MSC_VER #pragma omp parallel num_threads(num_threads) { #pragma omp single nowait { - // kdtree.root = create_node(kdtree, node_count, points, kdtree.indices.begin(), kdtree.indices.begin(), kdtree.indices.end()); } } +#else + kdtree.root = create_node(kdtree, node_count, points, kdtree.indices.begin(), kdtree.indices.begin(), kdtree.indices.end()); +#endif kdtree.nodes.resize(node_count); } @@ -74,11 +83,16 @@ struct KdTreeBuilderOMP { node.node_type.sub.thresh = proj(traits::point(points, *median_itr)); // Create left and right child nodes. +#ifndef _MSC_VER #pragma omp task default(shared) if (N > 512) node.left = create_node(kdtree, node_count, points, global_first, first, median_itr); #pragma omp task default(shared) if (N > 512) node.right = create_node(kdtree, node_count, points, global_first, median_itr, last); #pragma omp taskwait +#else + node.left = create_node(kdtree, node_count, points, global_first, first, median_itr); + node.right = create_node(kdtree, node_count, points, global_first, median_itr, last); +#endif return node_index; } diff --git a/include/small_gicp/ann/projection.hpp b/include/small_gicp/ann/projection.hpp index ab40579..9d58457 100644 --- a/include/small_gicp/ann/projection.hpp +++ b/include/small_gicp/ann/projection.hpp @@ -34,7 +34,9 @@ struct AxisAlignedProjection { Eigen::Vector4d sum_sq = Eigen::Vector4d::Zero(); const size_t step = N < setting.max_scan_count ? 1 : N / setting.max_scan_count; - for (auto itr = first; itr < last; itr += step) { + const size_t num_steps = N / step; + for (int i = 0; i < num_steps; i++) { + const auto itr = first + step * i; const Eigen::Vector4d pt = traits::point(points, *itr); sum_pt += pt; sum_sq += pt.cwiseProduct(pt); @@ -71,7 +73,9 @@ struct NormalProjection { Eigen::Matrix4d sum_sq = Eigen::Matrix4d::Zero(); const size_t step = N < setting.max_scan_count ? 1 : N / setting.max_scan_count; - for (auto itr = first; itr < last; itr += step) { + const size_t num_steps = N / step; + for (int i = 0; i < num_steps; i++) { + const auto itr = first + step * i; const Eigen::Vector4d pt = traits::point(points, *itr); sum_pt += pt; sum_sq += pt * pt.transpose();