-
Notifications
You must be signed in to change notification settings - Fork 286
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
Fix Argobots support #4421
Fix Argobots support #4421
Conversation
test:jenkins/ch3/tcp |
test:jenkins/ch4/argobots |
test:jenkins/ch4/ofi |
@@ -1192,6 +1192,8 @@ extern MPID_Thread_mutex_t mpi_t_mutex; | |||
do { \ | |||
int err_; \ | |||
MPIR_T_THREAD_CHECK_BEGIN \ | |||
MPID_Thread_init(&err_); \ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can argobot init be called multiple times?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes. It is okay to call it multiple times (internally there's a refcount).
If it wouldn't be the case, MPL_thread_init()
will take care of it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This concern is mentioned in src/mpl/include/mpl_thread_argobots.h
.
I added |
test:jenkins/ch4/argobots |
23fc7c3
to
8d0bd77
Compare
test:jenkins/ch4/argobots |
test/mpi/util/mtest_thread_abt.h
Outdated
/* Reference counter */ | ||
|
||
static void MTest_abt_incr_refcount(void); | ||
static void MTest_abt_decr_refcount(void); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I understand this is only included in mtest_thread.c
, but it is concerning to have static implementation inside a .h
header.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In terms of coding practice, I believe non-static/inline definitions should be avoided since it often causes a "multiple definition" error.
In this specific case, static means these functions cannot be called by individual tests.
test/mpi/util/mtest_thread_abt.h
Outdated
|
||
static void MTest_abt_incr_refcount(void) | ||
{ | ||
MTest_abt_acquire_spinlock(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will it work without the lock?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Lock initialization might happen in created threads, so this spinlock is necessary.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is beyond simple. It adds the lazy initialization logic, then the concern of checking and initialization inside the spawned threads, then the concern of using spin-lock, and then the concern of atomics. I much prefer solution #2 at this point.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you. I got it. I will adopt solution #2.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This has been fixed by #4429, so this PR no longer contains it.
8d0bd77
to
a454606
Compare
test:mpich/ch4/argobots |
test:mpich/ch4/argobots |
1 similar comment
test:mpich/ch4/argobots |
When multithreaded MPI is enabled, MPI_T_init_thread() needs to initialize a mutex, mpi_t_mutex. This mutex should be created after initializing MPL/thread, which is especially necessary when the underlying threads are not Pthreads (e.g., Argobots threads). This patch adds initialization and finalization of MPL/thread in MPI_T_init_thread() and MPI_T_finalize().
When underlying threads are nonpreemptive (e.g., Argobots threads), a busy loop can cause a deadlock. This patch fixes a busy loop in threads/idup_deadlock by adding MTest_thread_yield(), a new function that is translated into yield when threads are nonpreemptive.
The default stack size of Argobots threads is too small and can cause a stack overflow bug. This patch fixes it.
dc8a0df
to
0e18727
Compare
test:mpich/ch4/argobots |
0e18727
to
a803757
Compare
test:mpich/ch4/argobots |
a803757
to
440590e
Compare
test:mpich/ch4/argobots |
440590e
to
c3561d7
Compare
test:mpich/ch4/argobots |
test:mpich/ch4/argobots |
test:mpich/ch4/ofi |
Finally all checks passed. @hzhou could you please take a look at this PR when you have time? |
Sure, I'll review it tomorrow. Thank you for the effort. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good. Just a minor comment. I am approving it. There is no need to rerun the tests if you just amend the comment.
@@ -101,6 +101,10 @@ int main(int argc, char *argv[]) | |||
#endif /* USE_THREADS */ | |||
|
|||
#ifdef USE_THREADS | |||
/* Initialize the thread package. It should not be initialized via | |||
* MTest_Init_thread since MTest_Finalize cannot be called. */ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is because both MTest_Init_thread
and MTest_Finalize
are not called rather than cannot be called, right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You are right. I will change the comment. Thanks a lot for reviewing this PR!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@hzhou I fixed the comment.
th_taskmaster.c uses MTest thread functions for forking and joining threads, but the thread package is not initialized. This patch fixes it. Note that we cannot explicitly call MTest_Init_thread() since the corresponding MTest_Finalize() prints "No Errors" as many as spawned MPI processes, breaking this test.
c3561d7
to
f220643
Compare
@@ -41,6 +41,7 @@ MTEST_THREAD_RETURN_TYPE test_comm_dup(void *arg) | |||
wait = 0; | |||
for (i = 0; i < NUM_THREADS; i++) | |||
wait += start_idup[i]; | |||
MTest_thread_yield(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@shintaro-iwasaki MTest_thread_yield()
is not in a header file that is included in idup_deadlock.c
, causing a compiler warning. Could you fix it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oops I missed it. #4503 should fix it. Thanks!
It was missed in pmodels#4421.
This patch adds MTest_thread_yield() to tests that I missed in pmodels#4421. Note this does not affect the program behavior if OS-level threads (Pthreads) are used because MTest_thread_yield() is mapped to no-op.
This patch adds MTest_thread_yield() to tests that I missed in pmodels#4421. Note this does not affect the program behavior if OS-level threads (Pthreads) are used because MTest_thread_yield() is mapped to no-op.
Pull Request Description
This PR fixes Argobots support.
Fix
mpl/include/mpl_thread_argobots.h
This change will not affect the default Pthreads behavior.
Call
MPID_Thread_init()
inMPI_T_init_thread()
Any
MPID_Thread_
operations should be called afterMPID_Thread_init()
. This will not affect the default Pthreads behavior since the Pthreads version does nothing inMPID_Thread_init()
.MPI_T_init_thread()
can be called beforeMPI_Init_thread()
, soMPI_T_init_thread()
needs its ownMPID_Thread_init()
.Add
yield()
to a busy loop intest/mpi/threads/comm/idup_deadlock
Nonpreemptive threads (e.g., Argobots threads) can cause a deadlock if there is a busy loop. This PR adds a new yield function (
MTest_thread_yield()
) and inserts it into a busy loop intest/mpi/threads/comm/idup_deadlock
.This will not affect the default Pthreads behavior since the Pthreads version does nothing in
MTest_thread_yield()
.Note
Regarding
3. MTest_thread_yield()
, there are many options.1.a. [What this PR does] Add
MTest_thread_yield()
, which callsyield()
only when the underlying thread is nonpreemptive.1.b. Add
MTest_thread_scheduling_point()
(instead ofMTest_thread_yield()
). The functionality is the same as that of 1.a.1.c. Add
MTest_thread_yield()
, which callsyield()
even with Pthreads (e.g.,pthread_yield()
).MTest_thread_lock()
).Expected Impact
No performance difference for the default Pthreads version.
Author Checklist
Fixes test/mpich/threads: MTest_init_thread_pkg() is not called. #4422.
module: short description
and follows good practicedoc/
directory for any new code design