int MPIR_Comm_set_info_impl(MPID_Comm * comm_ptr, MPID_Info * info_ptr) { int mpi_errno = MPI_SUCCESS; MPID_Info *curr_info = NULL; MPID_MPI_STATE_DECL(MPID_STATE_MPIR_COMM_SET_INFO_IMPL); MPID_MPI_FUNC_ENTER(MPID_STATE_MPIR_COMM_SET_INFO_IMPL); mpi_errno = MPIR_Comm_apply_hints(comm_ptr, info_ptr); if (mpi_errno != MPI_SUCCESS) goto fn_fail; if (comm_ptr->info == NULL) { /* Always have at least a blank info hint. */ mpi_errno = MPIU_Info_alloc(&(comm_ptr->info)); if (mpi_errno != MPI_SUCCESS) goto fn_fail; } /* MPIR_Info_set_impl will do an O(n) search to prevent duplicate keys, so * this _FOREACH loop will cost O(m*n) time, where "m" is the number of keys * in info_ptr and "n" is the number of keys in comm_ptr->info. */ MPL_LL_FOREACH(info_ptr, curr_info) { /* Have we hit the default, empty info hint? */ if (curr_info->key == NULL) continue; mpi_errno = MPIR_Info_set_impl(comm_ptr->info, curr_info->key, curr_info->value); if (mpi_errno) MPIU_ERR_POP(mpi_errno); } fn_exit: return mpi_errno; fn_fail: goto fn_exit; }
/*@ MPI_Info_create - Creates a new info object Output Parameters: . info - info object created (handle) .N ThreadSafe .N Fortran .N Errors .N MPI_SUCCESS .N MPI_ERR_OTHER @*/ int MPI_Info_create( MPI_Info *info ) { MPID_Info *info_ptr; static const char FCNAME[] = "MPI_Info_create"; int mpi_errno = MPI_SUCCESS; MPID_MPI_STATE_DECL(MPID_STATE_MPI_INFO_CREATE); MPIR_ERRTEST_INITIALIZED_ORDIE(); MPID_THREAD_CS_ENTER(GLOBAL, MPIR_THREAD_GLOBAL_ALLFUNC_MUTEX); MPID_MPI_FUNC_ENTER(MPID_STATE_MPI_INFO_CREATE); /* Validate parameters and objects (post conversion) */ # ifdef HAVE_ERROR_CHECKING { MPID_BEGIN_ERROR_CHECKS; { MPIR_ERRTEST_ARGNULL(info, "info", mpi_errno); } MPID_END_ERROR_CHECKS; } # endif /* HAVE_ERROR_CHECKING */ /* ... body of routine ... */ mpi_errno = MPIU_Info_alloc(&info_ptr); if (mpi_errno) MPIR_ERR_POP(mpi_errno); *info = info_ptr->handle; /* (info_ptr)->cookie = MPIR_INFO_COOKIE; */ /* this is the first structure in this linked list. it is always kept empty. new (key,value) pairs are added after it. */ /* ... end of body of routine ... */ fn_exit: MPID_MPI_FUNC_EXIT(MPID_STATE_MPI_INFO_CREATE); MPID_THREAD_CS_EXIT(GLOBAL, MPIR_THREAD_GLOBAL_ALLFUNC_MUTEX); return mpi_errno; fn_fail: /* --BEGIN ERROR HANDLING-- */ # ifdef HAVE_ERROR_CHECKING { mpi_errno = MPIR_Err_create_code( mpi_errno, MPIR_ERR_RECOVERABLE, FCNAME, __LINE__, MPI_ERR_OTHER, "**mpi_info_create", "**mpi_info_create %p", info); } # endif mpi_errno = MPIR_Err_return_comm( NULL, FCNAME, mpi_errno ); goto fn_exit; /* --END ERROR HANDLING-- */ }
int MPIR_Comm_get_info_impl(MPID_Comm * comm_ptr, MPID_Info ** info_p_p) { int mpi_errno = MPI_SUCCESS; /* Allocate an empty info object */ mpi_errno = MPIU_Info_alloc(info_p_p); if (mpi_errno != MPI_SUCCESS) goto fn_fail; fn_exit: return mpi_errno; fn_fail: goto fn_exit; }
int MPIR_Info_dup_impl(MPID_Info *info_ptr, MPID_Info **new_info_ptr) { int mpi_errno = MPI_SUCCESS; MPID_Info *curr_old, *curr_new; *new_info_ptr = NULL; if (!info_ptr) goto fn_exit; /* Note that this routine allocates info elements one at a time. In the multithreaded case, each allocation may need to acquire and release the allocation lock. If that is ever a problem, we may want to add an "allocate n elements" routine and execute this it two steps: count and then allocate */ /* FIXME : multithreaded */ mpi_errno = MPIU_Info_alloc(&curr_new); if (mpi_errno) MPIR_ERR_POP(mpi_errno); *new_info_ptr = curr_new; curr_old = info_ptr->next; while (curr_old) { mpi_errno = MPIU_Info_alloc(&curr_new->next); if (mpi_errno) MPIR_ERR_POP(mpi_errno); curr_new = curr_new->next; curr_new->key = MPIU_Strdup(curr_old->key); curr_new->value = MPIU_Strdup(curr_old->value); curr_old = curr_old->next; } fn_exit: return mpi_errno; fn_fail: goto fn_exit; }
int MPIR_Info_set_impl(MPID_Info *info_ptr, const char *key, const char *value) { int mpi_errno = MPI_SUCCESS; MPID_Info *curr_ptr, *prev_ptr; MPID_MPI_STATE_DECL(MPID_STATE_MPIR_INFO_SET_IMPL); MPID_MPI_FUNC_ENTER(MPID_STATE_MPIR_INFO_SET_IMPL); prev_ptr = info_ptr; curr_ptr = info_ptr->next; while (curr_ptr) { if (!strncmp(curr_ptr->key, key, MPI_MAX_INFO_KEY)) { /* Key already present; replace value */ MPL_free(curr_ptr->value); curr_ptr->value = MPL_strdup(value); break; } prev_ptr = curr_ptr; curr_ptr = curr_ptr->next; } if (!curr_ptr) { /* Key not present, insert value */ mpi_errno = MPIU_Info_alloc(&curr_ptr); if (mpi_errno) MPIR_ERR_POP(mpi_errno); /*printf( "Inserting new elm %x at %x\n", curr_ptr->id, prev_ptr->id );*/ prev_ptr->next = curr_ptr; curr_ptr->key = MPL_strdup(key); curr_ptr->value = MPL_strdup(value); } fn_exit: MPID_MPI_FUNC_EXIT(MPID_STATE_MPIR_INFO_SET_IMPL); return mpi_errno; fn_fail: goto fn_exit; }