Commit 40862985 authored by Wesley Bland's avatar Wesley Bland Committed by Antonio J. Pena
Browse files

Improve error checking for buffer aliasing



If the user isn't using MPI_IN_PLACE when they should, this check will do a
better job of warning them about it.

See #2049
Signed-off-by: default avatarAntonio J. Pena <apenya@mcs.anl.gov>
parent 00f452cd
......@@ -862,6 +862,8 @@ int MPI_Ireduce(const void *sendbuf, void *recvbuf, int count, MPI_Datatype data
{
MPID_BEGIN_ERROR_CHECKS
{
int rank;
MPID_Comm_valid_ptr(comm_ptr, mpi_errno);
if (HANDLE_GET_KIND(datatype) != HANDLE_KIND_BUILTIN) {
MPID_Datatype *datatype_ptr = NULL;
......@@ -883,7 +885,24 @@ int MPI_Ireduce(const void *sendbuf, void *recvbuf, int count, MPI_Datatype data
if (mpi_errno != MPI_SUCCESS) goto fn_fail;
MPIR_ERRTEST_ARGNULL(request,"request", mpi_errno);
/* TODO more checks may be appropriate (counts, in_place, buffer aliasing, etc) */
if (comm_ptr->comm_kind == MPID_INTRACOMM) {
if (sendbuf != MPI_IN_PLACE)
MPIR_ERRTEST_USERBUFFER(sendbuf,count,datatype,mpi_errno);
rank = comm_ptr->rank;
if (rank == root) {
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, count, mpi_errno);
MPIR_ERRTEST_USERBUFFER(recvbuf,count,datatype,mpi_errno);
if (count != 0 && sendbuf != MPI_IN_PLACE) {
MPIR_ERRTEST_ALIAS_COLL(sendbuf, recvbuf, mpi_errno);
}
}
else
MPIR_ERRTEST_SENDBUF_INPLACE(sendbuf, count, mpi_errno);
}
/* TODO more checks may be appropriate (counts, in_place, etc) */
}
MPID_END_ERROR_CHECKS
}
......
......@@ -441,7 +441,10 @@ int MPI_Iscan(const void *sendbuf, void *recvbuf, int count, MPI_Datatype dataty
if (mpi_errno != MPI_SUCCESS) goto fn_fail;
MPIR_ERRTEST_ARGNULL(request,"request", mpi_errno);
/* TODO more checks may be appropriate (counts, in_place, buffer aliasing, etc) */
if (sendbuf != MPI_IN_PLACE)
MPIR_ERRTEST_ALIAS_COLL(sendbuf, recvbuf, mpi_errno);
/* TODO more checks may be appropriate (counts, in_place, etc) */
}
MPID_END_ERROR_CHECKS
}
......
......@@ -665,8 +665,11 @@ int MPI_Iscatter(const void *sendbuf, int sendcount, MPI_Datatype sendtype,
MPIR_ERRTEST_SENDBUF_INPLACE(sendbuf, sendcount, mpi_errno);
/* catch common aliasing cases */
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcount == recvcount && recvcount != 0)
MPIR_ERRTEST_ALIAS_COLL(sendbuf,recvbuf,mpi_errno);
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcount == recvcount && recvcount != 0) {
int sendtype_size;
MPID_Datatype_get_size_macro(sendtype, sendtype_size);
MPIR_ERRTEST_ALIAS_COLL(recvbuf, (char*)sendbuf + comm_ptr->rank*sendcount*sendtype_size, mpi_errno);
}
}
else
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcount, mpi_errno);
......
......@@ -256,6 +256,13 @@ int MPI_Iscatterv(const void *sendbuf, const int sendcounts[], const int displs[
break;
}
}
/* catch common aliasing cases */
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcounts[comm_ptr->rank] != 0 && recvcount != 0) {
int sendtype_size;
MPID_Datatype_get_size_macro(sendtype, sendtype_size);
MPIR_ERRTEST_ALIAS_COLL(recvbuf, (char*)sendbuf + displs[comm_ptr->rank]*sendtype_size, mpi_errno);
}
}
else
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcount, mpi_errno);
......
......@@ -1172,8 +1172,10 @@ int MPI_Reduce_scatter(const void *sendbuf, void *recvbuf, const int recvcounts[
}
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcounts[comm_ptr->rank], mpi_errno);
if (comm_ptr->comm_kind == MPID_INTERCOMM)
if (comm_ptr->comm_kind == MPID_INTERCOMM) {
MPIR_ERRTEST_SENDBUF_INPLACE(sendbuf, sum, mpi_errno);
} else if (sendbuf != MPI_IN_PLACE)
MPIR_ERRTEST_ALIAS_COLL(sendbuf, recvbuf, mpi_errno)
MPIR_ERRTEST_USERBUFFER(recvbuf,recvcounts[comm_ptr->rank],datatype,mpi_errno);
MPIR_ERRTEST_USERBUFFER(sendbuf,sum,datatype,mpi_errno);
......
......@@ -1136,8 +1136,10 @@ int MPI_Reduce_scatter_block(const void *sendbuf, void *recvbuf,
}
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcount, mpi_errno);
if (comm_ptr->comm_kind == MPID_INTERCOMM)
if (comm_ptr->comm_kind == MPID_INTERCOMM) {
MPIR_ERRTEST_SENDBUF_INPLACE(sendbuf, recvcount, mpi_errno);
} else if (sendbuf != MPI_IN_PLACE)
MPIR_ERRTEST_ALIAS_COLL(sendbuf, recvbuf, mpi_errno)
MPIR_ERRTEST_USERBUFFER(recvbuf,recvcount,datatype,mpi_errno);
MPIR_ERRTEST_USERBUFFER(sendbuf,recvcount,datatype,mpi_errno);
......
......@@ -548,6 +548,9 @@ int MPI_Scan(const void *sendbuf, void *recvbuf, int count, MPI_Datatype datatyp
( * MPIR_OP_HDL_TO_DTYPE_FN(op) )(datatype);
}
if (mpi_errno != MPI_SUCCESS) goto fn_fail;
if (sendbuf != MPI_IN_PLACE)
MPIR_ERRTEST_ALIAS_COLL(sendbuf, recvbuf, mpi_errno);
}
MPID_END_ERROR_CHECKS;
}
......
......@@ -724,10 +724,13 @@ int MPI_Scatter(const void *sendbuf, int sendcount, MPI_Datatype sendtype,
MPIR_ERRTEST_SENDBUF_INPLACE(sendbuf, sendcount, mpi_errno);
/* catch common aliasing cases */
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcount == recvcount && recvcount != 0)
MPIR_ERRTEST_ALIAS_COLL(sendbuf,recvbuf,mpi_errno);
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcount == recvcount && recvcount != 0) {
int sendtype_size;
MPID_Datatype_get_size_macro(sendtype, sendtype_size);
MPIR_ERRTEST_ALIAS_COLL(recvbuf, (char*)sendbuf + comm_ptr->rank*sendcount*sendtype_size, mpi_errno);
}
}
else
else
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcount, mpi_errno);
if (recvbuf != MPI_IN_PLACE) {
......
......@@ -293,6 +293,12 @@ int MPI_Scatterv(const void *sendbuf, const int *sendcounts, const int *displs,
break;
}
}
/* catch common aliasing cases */
if (recvbuf != MPI_IN_PLACE && sendtype == recvtype && sendcounts[comm_ptr->rank] != 0 && recvcount != 0) {
int sendtype_size;
MPID_Datatype_get_size_macro(sendtype, sendtype_size);
MPIR_ERRTEST_ALIAS_COLL(recvbuf, (char*)sendbuf + displs[comm_ptr->rank]*sendtype_size, mpi_errno);
}
}
else
MPIR_ERRTEST_RECVBUF_INPLACE(recvbuf, recvcount, mpi_errno);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment