Fix undefined behaviour caused by uncaught exceptions in OMP section

An OpenMP parallel section must have a single entry and a single point
of exit. Leaving such a section by throwing an exception is undefined.
This patch fixes this by catching possible exceptions on the parallel
section and throwing right we left it.
This commit is contained in:
David Tellenbach 2020-10-02 00:41:01 +02:00
parent b933946d63
commit 9f202c6f1e
2 changed files with 12 additions and 4 deletions

View File

@ -132,7 +132,8 @@ void parallelize_gemm(const Functor& func, Index rows, Index cols, Index depth,
ei_declare_aligned_stack_constructed_variable(GemmParallelInfo<Index>,info,threads,0); ei_declare_aligned_stack_constructed_variable(GemmParallelInfo<Index>,info,threads,0);
#pragma omp parallel num_threads(threads) int errorCount = 0;
#pragma omp parallel num_threads(threads) reduction(+: errorCount)
{ {
Index i = omp_get_thread_num(); Index i = omp_get_thread_num();
// Note that the actual number of threads might be lower than the number of request ones. // Note that the actual number of threads might be lower than the number of request ones.
@ -151,9 +152,14 @@ void parallelize_gemm(const Functor& func, Index rows, Index cols, Index depth,
info[i].lhs_start = r0; info[i].lhs_start = r0;
info[i].lhs_length = actualBlockRows; info[i].lhs_length = actualBlockRows;
EIGEN_TRY {
if(transpose) func(c0, actualBlockCols, 0, rows, info); if(transpose) func(c0, actualBlockCols, 0, rows, info);
else func(0, rows, c0, actualBlockCols, info); else func(0, rows, c0, actualBlockCols, info);
} EIGEN_CATCH(...) {
++errorCount;
} }
}
if (errorCount) EIGEN_THROW_X(Eigen::eigen_assert_exception());
#endif #endif
} }

View File

@ -109,5 +109,7 @@ void memoryleak()
void test_exceptions() void test_exceptions()
{ {
EIGEN_TRY {
CALL_SUBTEST( memoryleak() ); CALL_SUBTEST( memoryleak() );
} EIGEN_CATCH(...) {}
} }