Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for limiting num_threads in tbb task #252

Merged
merged 50 commits into from
Mar 18, 2024
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
Show all changes
50 commits
Select commit Hold shift + click to select a range
5e08b68
Add support for limiting num_threads in tbb task
dch4o Nov 2, 2023
fae5b46
Merge remote-tracking branch 'origin/main' into feature/set-num-threads
nachovizzo Feb 11, 2024
24964c8
Make num_threads a paramter of the voxel hash map
nachovizzo Feb 11, 2024
51decb1
This got a bit more hacky but is to avoid hardocding a praamter
nachovizzo Feb 11, 2024
b327258
Propagate max_threads to Python config
nachovizzo Feb 11, 2024
a262e9f
Merge remote-tracking branch 'origin/main' into feature/set-num-threads
nachovizzo Feb 29, 2024
e5044f8
First draft on core library
nachovizzo Mar 1, 2024
6c7e505
Update python API
nachovizzo Mar 1, 2024
80248bb
Rearange
nachovizzo Mar 1, 2024
505ab61
Remove type alias
nachovizzo Mar 1, 2024
1dc13a7
Fix build
nachovizzo Mar 1, 2024
5053877
Wrap constants into a configuration struct
nachovizzo Mar 1, 2024
0e015d9
Split the watters
nachovizzo Mar 1, 2024
d4378b4
It's all about drafts
nachovizzo Mar 1, 2024
ebdfab5
Update python API
nachovizzo Mar 1, 2024
598e1a6
Some renaming just because
nachovizzo Mar 1, 2024
18465fd
Changing names trying to auto-convince myself...
nachovizzo Mar 1, 2024
3606d0c
Fix c++ build
nachovizzo Mar 1, 2024
9fa9f2d
rename function
benemer Mar 4, 2024
ea7b313
renaming variables
benemer Mar 4, 2024
5c8fc25
renaming, should be one neighbor only
benemer Mar 4, 2024
01b11c5
Tizianified a little bit
tizianoGuadagnino Mar 4, 2024
f4a2465
Draft on voxelhashmap
nachovizzo Mar 4, 2024
0cb69a7
Rename
nachovizzo Mar 4, 2024
39e4cbf
Rename Correspondences -> Associations
nachovizzo Mar 4, 2024
b434e04
Move stuff around only
nachovizzo Mar 4, 2024
70a6457
Remove redunant name
nachovizzo Mar 4, 2024
876fedc
They are not there, we need to find them!
nachovizzo Mar 4, 2024
c338afb
Shrink
nachovizzo Mar 4, 2024
2b79370
Tiziano shows to guys -> with for_each
tizianoGuadagnino Mar 4, 2024
d834170
Tiziano shows to guys -> with transform_reduce....sexy
tizianoGuadagnino Mar 4, 2024
b58d352
Merge remote-tracking branch 'origin/nacho/strip_nn_search_from_voxel…
nachovizzo Mar 5, 2024
f88310f
Consistent naming
nachovizzo Mar 5, 2024
8fb80db
Bring comments for readbilty
nachovizzo Mar 5, 2024
f5c1524
rename variable
nachovizzo Mar 5, 2024
318cd86
Sacrifice name for one-liner
nachovizzo Mar 5, 2024
0c823ae
AlignCloudToMap -> AlignPointsToMap
nachovizzo Mar 5, 2024
7a45c9d
Make rename like a book on ProbRob
tizianoGuadagnino Mar 5, 2024
26dd7b0
Revert "Make rename like a book on ProbRob"
nachovizzo Mar 5, 2024
d5a38f4
estimation_threshold -> convergence_criterion
nachovizzo Mar 5, 2024
f2e5d60
Rename threshold also here
benemer Mar 5, 2024
9a80e16
Merge remote-tracking branch 'origin/nacho/strip_nn_search_from_voxel…
nachovizzo Mar 5, 2024
cdafca9
Merge remote-tracking branch 'origin/nacho/strip_nn_search_from_voxel…
nachovizzo Mar 5, 2024
cfadfab
no typos no nacho
nachovizzo Mar 5, 2024
bd063e9
Remove comment
nachovizzo Mar 5, 2024
90e6fc5
Merge remote-tracking branch 'origin/nacho/strip_nn_search_from_voxel…
nachovizzo Mar 5, 2024
cbc831c
Merge remote-tracking branch 'origin/main' into feature/set-num-threads
nachovizzo Mar 5, 2024
af2c31a
reduce diff
nachovizzo Mar 5, 2024
f550a1a
Small improvement. max_num_threads_ always represents what it says
nachovizzo Mar 11, 2024
bb880fd
Remove single letter variable
tizianoGuadagnino Mar 18, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 32 additions & 25 deletions cpp/kiss_icp/core/Registration.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,10 @@
// SOFTWARE.
#include "Registration.hpp"

#include <oneapi/tbb/task_arena.h>
#include <tbb/blocked_range.h>
#include <tbb/parallel_reduce.h>
#include <tbb/task_arena.h>

#include <algorithm>
#include <cmath>
Expand Down Expand Up @@ -68,7 +70,8 @@ constexpr double ESTIMATION_THRESHOLD_ = 0.0001;
std::tuple<Eigen::Matrix6d, Eigen::Vector6d> BuildLinearSystem(
const std::vector<Eigen::Vector3d> &source,
const std::vector<Eigen::Vector3d> &target,
double kernel) {
double kernel,
int max_threads = tbb::task_arena::automatic) {
nachovizzo marked this conversation as resolved.
Show resolved Hide resolved
auto compute_jacobian_and_residual = [&](auto i) {
const Eigen::Vector3d residual = source[i] - target[i];
Eigen::Matrix3_6d J_r;
Expand All @@ -77,29 +80,33 @@ std::tuple<Eigen::Matrix6d, Eigen::Vector6d> BuildLinearSystem(
return std::make_tuple(J_r, residual);
};

const auto &[JTJ, JTr] = tbb::parallel_reduce(
// Range
tbb::blocked_range<size_t>{0, source.size()},
// Identity
ResultTuple(),
// 1st Lambda: Parallel computation
[&](const tbb::blocked_range<size_t> &r, ResultTuple J) -> ResultTuple {
auto Weight = [&](double residual2) {
return square(kernel) / square(kernel + residual2);
};
auto &[JTJ_private, JTr_private] = J;
for (auto i = r.begin(); i < r.end(); ++i) {
const auto &[J_r, residual] = compute_jacobian_and_residual(i);
const double w = Weight(residual.squaredNorm());
JTJ_private.noalias() += J_r.transpose() * w * J_r;
JTr_private.noalias() += J_r.transpose() * w * residual;
}
return J;
},
// 2nd Lambda: Parallel reduction of the private Jacboians
[&](ResultTuple a, const ResultTuple &b) -> ResultTuple { return a + b; });

return std::make_tuple(JTJ, JTr);
ResultTuple jacobian;
tbb::task_arena limited_arena(max_threads);
limited_arena.execute([&]() -> void {
jacobian = tbb::parallel_reduce(
// Range
tbb::blocked_range<size_t>{0, source.size()},
// Identity
ResultTuple(),
// 1st Lambda: Parallel computation
[&](const tbb::blocked_range<size_t> &r, ResultTuple J) -> ResultTuple {
auto Weight = [&](double residual2) {
return square(kernel) / square(kernel + residual2);
};
auto &[JTJ_private, JTr_private] = J;
for (auto i = r.begin(); i < r.end(); ++i) {
const auto &[J_r, residual] = compute_jacobian_and_residual(i);
const double w = Weight(residual.squaredNorm());
JTJ_private.noalias() += J_r.transpose() * w * J_r;
JTr_private.noalias() += J_r.transpose() * w * residual;
}
return J;
},
// 2nd Lambda: Parallel reduction of the private Jacboians
[&](ResultTuple a, const ResultTuple &b) -> ResultTuple { return a + b; });
});

return std::make_tuple(jacobian.JTJ, jacobian.JTr);
}
} // namespace

Expand All @@ -122,7 +129,7 @@ Sophus::SE3d RegisterFrame(const std::vector<Eigen::Vector3d> &frame,
// Equation (10)
const auto &[src, tgt] = voxel_map.GetCorrespondences(source, max_correspondence_distance);
// Equation (11)
const auto &[JTJ, JTr] = BuildLinearSystem(src, tgt, kernel);
const auto &[JTJ, JTr] = BuildLinearSystem(src, tgt, kernel, voxel_map.max_threads_);
nachovizzo marked this conversation as resolved.
Show resolved Hide resolved
const Eigen::Vector6d dx = JTJ.ldlt().solve(-JTr);
const Sophus::SE3d estimation = Sophus::SE3d::exp(dx);
// Equation (12)
Expand Down
69 changes: 39 additions & 30 deletions cpp/kiss_icp/core/VoxelHashMap.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@

#include <tbb/blocked_range.h>
#include <tbb/parallel_reduce.h>
#include <tbb/task_arena.h>

#include <Eigen/Core>
#include <algorithm>
Expand All @@ -42,6 +43,7 @@ struct ResultTuple {
std::vector<Eigen::Vector3d> source;
std::vector<Eigen::Vector3d> target;
};

} // namespace

namespace kiss_icp {
Expand Down Expand Up @@ -90,39 +92,46 @@ VoxelHashMap::Vector3dVectorTuple VoxelHashMap::GetCorrespondences(

return closest_neighbor;
};

using points_iterator = std::vector<Eigen::Vector3d>::const_iterator;
const auto [source, target] = tbb::parallel_reduce(
// Range
tbb::blocked_range<points_iterator>{points.cbegin(), points.cend()},
// Identity
ResultTuple(points.size()),
// 1st lambda: Parallel computation
[max_correspondance_distance, &GetClosestNeighboor](
const tbb::blocked_range<points_iterator> &r, ResultTuple res) -> ResultTuple {
auto &[src, tgt] = res;
src.reserve(r.size());
tgt.reserve(r.size());
for (const auto &point : r) {
Eigen::Vector3d closest_neighboors = GetClosestNeighboor(point);
if ((closest_neighboors - point).norm() < max_correspondance_distance) {
src.emplace_back(point);
tgt.emplace_back(closest_neighboors);
ResultTuple correspondences(points.size());
tbb::task_arena limited_arena(max_threads_);
limited_arena.execute([&]() -> void {
correspondences = tbb::parallel_reduce(
// Range
tbb::blocked_range<points_iterator>{points.cbegin(), points.cend()},
// Identity
ResultTuple(points.size()),
// 1st lambda: Parallel computation
[max_correspondance_distance, &GetClosestNeighboor](
const tbb::blocked_range<points_iterator> &r, ResultTuple res) -> ResultTuple {
auto &[src, tgt] = res;
src.reserve(r.size());
tgt.reserve(r.size());
for (const auto &point : r) {
Eigen::Vector3d closest_neighboors = GetClosestNeighboor(point);
if ((closest_neighboors - point).norm() < max_correspondance_distance) {
src.emplace_back(point);
tgt.emplace_back(closest_neighboors);
}
}
}
return res;
},
// 2nd lambda: Parallel reduction
[](ResultTuple a, const ResultTuple &b) -> ResultTuple {
auto &[src, tgt] = a;
const auto &[srcp, tgtp] = b;
src.insert(src.end(), //
std::make_move_iterator(srcp.begin()), std::make_move_iterator(srcp.end()));
tgt.insert(tgt.end(), //
std::make_move_iterator(tgtp.begin()), std::make_move_iterator(tgtp.end()));
return a;
});
return res;
},
// 2nd lambda: Parallel reduction
[](ResultTuple a, const ResultTuple &b) -> ResultTuple {
auto &[src, tgt] = a;
const auto &[srcp, tgtp] = b;
src.insert(src.end(), //
std::make_move_iterator(srcp.begin()),
std::make_move_iterator(srcp.end()));
tgt.insert(tgt.end(), //
std::make_move_iterator(tgtp.begin()),
std::make_move_iterator(tgtp.end()));
return a;
});
});

return std::make_tuple(source, target);
return std::make_tuple(correspondences.source, correspondences.target);
}

std::vector<Eigen::Vector3d> VoxelHashMap::Pointcloud() const {
Expand Down
10 changes: 8 additions & 2 deletions cpp/kiss_icp/core/VoxelHashMap.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
// should at least acknoowledge the work from CT-ICP by giving a star on GitHub
#pragma once

#include <oneapi/tbb/task_arena.h>
#include <tsl/robin_map.h>

#include <Eigen/Core>
Expand All @@ -52,10 +53,14 @@ struct VoxelHashMap {
}
};

explicit VoxelHashMap(double voxel_size, double max_distance, int max_points_per_voxel)
explicit VoxelHashMap(double voxel_size,
double max_distance,
int max_points_per_voxel,
int max_threads = tbb::task_arena::automatic)
nachovizzo marked this conversation as resolved.
Show resolved Hide resolved
: voxel_size_(voxel_size),
max_distance_(max_distance),
max_points_per_voxel_(max_points_per_voxel) {}
max_points_per_voxel_(max_points_per_voxel),
max_threads_(max_threads) {}

Vector3dVectorTuple GetCorrespondences(const Vector3dVector &points,
double max_correspondance_distance) const;
Expand All @@ -70,6 +75,7 @@ struct VoxelHashMap {
double voxel_size_;
double max_distance_;
int max_points_per_voxel_;
int max_threads_;
tsl::robin_map<Voxel, VoxelBlock, VoxelHash> map_;
};
} // namespace kiss_icp
Loading