test(solvers): verify thread scope across retained size transitions
This commit is contained in:
@@ -193,6 +193,32 @@ TEST(MklPardisoSolver, RefactorizesWithoutLeakingState) {
|
|||||||
1.0e-10);
|
1.0e-10);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(MklPardisoSolver, SingleEquationScopeTransitionsBetweenRetainedSizes) {
|
||||||
|
const int previous = mkl_set_num_threads_local(0);
|
||||||
|
struct Restore {
|
||||||
|
int previous;
|
||||||
|
~Restore() { static_cast<void>(mkl_set_num_threads_local(previous)); }
|
||||||
|
} restore{previous};
|
||||||
|
const int default_threads = mkl_get_max_threads();
|
||||||
|
fesa::MklPardisoSolver solver;
|
||||||
|
ASSERT_TRUE(solver.Factorize(MakeDenseCsr(1U, {2.0})).IsOk());
|
||||||
|
auto single = MakeVector({0.0});
|
||||||
|
ASSERT_TRUE(solver.Solve(MakeVector({4.0}), single).IsOk());
|
||||||
|
EXPECT_DOUBLE_EQ(single[0U], 2.0);
|
||||||
|
ASSERT_TRUE(solver.Factorize(MakeDenseCsr(2U, {2, 0, 0, 3})).IsOk());
|
||||||
|
fesa::Vector pair{2U};
|
||||||
|
ASSERT_TRUE(solver.Solve(MakeVector({4, 6}), pair).IsOk());
|
||||||
|
EXPECT_NEAR(pair[0U], 2, 1e-14);
|
||||||
|
EXPECT_NEAR(pair[1U], 2, 1e-14);
|
||||||
|
EXPECT_EQ(mkl_get_max_threads(), default_threads);
|
||||||
|
EXPECT_EQ(mkl_set_num_threads_local(0), 0);
|
||||||
|
ASSERT_TRUE(solver.Factorize(MakeDenseCsr(1U, {4.0})).IsOk());
|
||||||
|
ASSERT_TRUE(solver.Solve(MakeVector({8.0}), single).IsOk());
|
||||||
|
EXPECT_DOUBLE_EQ(single[0U], 2.0);
|
||||||
|
EXPECT_EQ(mkl_get_max_threads(), default_threads);
|
||||||
|
EXPECT_EQ(mkl_set_num_threads_local(0), 0);
|
||||||
|
}
|
||||||
|
|
||||||
TEST(MklPardisoSolver, ClassifiesSingularIndefiniteAndNonfiniteFailures) {
|
TEST(MklPardisoSolver, ClassifiesSingularIndefiniteAndNonfiniteFailures) {
|
||||||
fesa::MklPardisoSolver solver;
|
fesa::MklPardisoSolver solver;
|
||||||
|
|
||||||
|
|||||||
@@ -205,4 +205,30 @@ TEST(TangentSolver, SingleEquationScopeRestoresTlsAcrossFreshFailureAndReuse) {
|
|||||||
EXPECT_TRUE(second.get());
|
EXPECT_TRUE(second.get());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(TangentSolver, SingleEquationScopeTransitionsBetweenRetainedSizes) {
|
||||||
|
const int previous = mkl_set_num_threads_local(0);
|
||||||
|
struct Restore {
|
||||||
|
int previous;
|
||||||
|
~Restore() { static_cast<void>(mkl_set_num_threads_local(previous)); }
|
||||||
|
} restore{previous};
|
||||||
|
const int default_threads = mkl_get_max_threads();
|
||||||
|
fesa::MklPardisoTangentSolver solver;
|
||||||
|
ASSERT_TRUE(solver.FactorizeFresh(MakeDenseCsr(1U, {2.0})).IsOk());
|
||||||
|
auto single = MakeVector({0.0});
|
||||||
|
ASSERT_TRUE(solver.SolveCorrection(MakeVector({4.0}), single).IsOk());
|
||||||
|
EXPECT_DOUBLE_EQ(single[0U], 2.0);
|
||||||
|
ASSERT_TRUE(solver.FactorizeFresh(MakeDenseCsr(2U, {2, 1, 0, 3})).IsOk());
|
||||||
|
fesa::Vector pair{2U};
|
||||||
|
ASSERT_TRUE(solver.SolveCorrection(MakeVector({6, 6}), pair).IsOk());
|
||||||
|
EXPECT_NEAR(pair[0U], 2, 1e-14);
|
||||||
|
EXPECT_NEAR(pair[1U], 2, 1e-14);
|
||||||
|
EXPECT_EQ(mkl_get_max_threads(), default_threads);
|
||||||
|
EXPECT_EQ(mkl_set_num_threads_local(0), 0);
|
||||||
|
ASSERT_TRUE(solver.FactorizeFresh(MakeDenseCsr(1U, {4.0})).IsOk());
|
||||||
|
ASSERT_TRUE(solver.SolveCorrection(MakeVector({8.0}), single).IsOk());
|
||||||
|
EXPECT_DOUBLE_EQ(single[0U], 2.0);
|
||||||
|
EXPECT_EQ(mkl_get_max_threads(), default_threads);
|
||||||
|
EXPECT_EQ(mkl_set_num_threads_local(0), 0);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|||||||
Reference in New Issue
Block a user