+++ /dev/null
-/* Copyright (c) 2013-2014. The SimGrid Team.
- * All rights reserved. */
-
-/* This program is free software; you can redistribute it and/or modify it
- * under the terms of the license (GNU LGPL) which comes with this package. */
-
-#include "colls_private.h"
-
-//#include <star-reduction.c>
-
-int smpi_coll_tuned_reduce_binomial(void *sendbuf, void *recvbuf, int count,
- MPI_Datatype datatype, MPI_Op op, int root,
- MPI_Comm comm)
-{
- MPI_Status status;
- int comm_size, rank;
- int mask, relrank, source;
- int dst;
- int tag = COLL_TAG_REDUCE;
- MPI_Aint extent;
- void *tmp_buf;
- MPI_Aint true_lb, true_extent;
- if (count == 0)
- return 0;
- rank = smpi_comm_rank(comm);
- comm_size = smpi_comm_size(comm);
-
- extent = smpi_datatype_get_extent(datatype);
-
- tmp_buf = (void *) smpi_get_tmp_sendbuffer(count * extent);
- int is_commutative = smpi_op_is_commute(op);
- mask = 1;
-
- int lroot;
- if (is_commutative)
- lroot = root;
- else
- lroot = 0;
- relrank = (rank - lroot + comm_size) % comm_size;
-
- smpi_datatype_extent(datatype, &true_lb, &true_extent);
-
- /* adjust for potential negative lower bound in datatype */
- tmp_buf = (void *)((char*)tmp_buf - true_lb);
-
- /* If I'm not the root, then my recvbuf may not be valid, therefore
- I have to allocate a temporary one */
- if (rank != root) {
- recvbuf = (void *) smpi_get_tmp_recvbuffer(count*(MAX(extent,true_extent)));
- recvbuf = (void *)((char*)recvbuf - true_lb);
- }
- if ((rank != root) || (sendbuf != MPI_IN_PLACE)) {
- smpi_datatype_copy(sendbuf, count, datatype, recvbuf,count, datatype);
- }
-
- while (mask < comm_size) {
- /* Receive */
- if ((mask & relrank) == 0) {
- source = (relrank | mask);
- if (source < comm_size) {
- source = (source + lroot) % comm_size;
- smpi_mpi_recv(tmp_buf, count, datatype, source, tag, comm, &status);
-
- if (is_commutative) {
- smpi_op_apply(op, tmp_buf, recvbuf, &count, &datatype);
- } else {
- smpi_op_apply(op, recvbuf, tmp_buf, &count, &datatype);
- smpi_datatype_copy(tmp_buf, count, datatype,recvbuf, count, datatype);
- }
- }
- } else {
- dst = ((relrank & (~mask)) + lroot) % comm_size;
- smpi_mpi_send(recvbuf, count, datatype, dst, tag, comm);
- break;
- }
- mask <<= 1;
- }
-
- if (!is_commutative && (root != 0)){
- if (rank == 0){
- smpi_mpi_send(recvbuf, count, datatype, root,tag, comm);
- }else if (rank == root){
- smpi_mpi_recv(recvbuf, count, datatype, 0, tag, comm, &status);
- }
- }
-
- if (rank != root) {
- smpi_free_tmp_buffer(recvbuf);
- }
- smpi_free_tmp_buffer(tmp_buf);
-
- return 0;
-}