14#include "arcane/materials/MeshMaterialVariableSynchronizerList.h" 
   16#include "arcane/utils/ITraceMng.h" 
   17#include "arcane/utils/NotSupportedException.h" 
   18#include "arcane/utils/ValueConvert.h" 
   19#include "arcane/utils/MemoryRessource.h" 
   20#include "arcane/utils/FatalErrorException.h" 
   22#include "arcane/core/IParallelMng.h" 
   23#include "arcane/core/IVariableSynchronizer.h" 
   24#include "arcane/core/internal/IParallelMngInternal.h" 
   25#include "arcane/core/materials/IMeshMaterialMng.h" 
   26#include "arcane/core/materials/internal/IMeshMaterialVariableInternal.h" 
   27#include "arcane/core/materials/internal/IMeshMaterialMngInternal.h" 
   29#include "arcane/materials/MeshMaterialVariable.h" 
   30#include "arcane/materials/IMeshMaterialSynchronizeBuffer.h" 
   31#include "arcane/materials/IMeshMaterialVariableSynchronizer.h" 
   33#include "arcane/accelerator/core/RunQueue.h" 
   42namespace MP = Arccore::MessagePassing;
 
   54  bool use_generic_version = 
false;
 
   55  Int32 sync_version = 0;
 
   57  Int64 message_total_size = 0;
 
   59  MP::MessageTag message_tag;
 
 
   70  : m_material_mng(material_mng)
 
   75      m_use_generic_version = (v.value() == 0);
 
   83  Int64 m_total_size = 0;
 
   84  bool m_use_generic_version = 
true;
 
   88  bool m_is_in_sync = 
false;
 
 
   94MeshMaterialVariableSynchronizerList::
 
   96: m_p(new 
Impl(material_mng))
 
  103MeshMaterialVariableSynchronizerList::
 
  104~MeshMaterialVariableSynchronizerList()
 
  115  return m_p->m_total_size;
 
 
  127  Int32 v = m_p->m_material_mng->synchronizeVariableVersion();
 
  128  bool is_blocking = (v == 8);
 
  130  _beginSynchronize(is_blocking);
 
  131  _endSynchronize(is_blocking);
 
 
  140  Int32 v = m_p->m_material_mng->synchronizeVariableVersion();
 
  142    ARCANE_FATAL(
"beginSynchronize() is only valid for synchronize version 7 (v={0})", v);
 
  143  _beginSynchronize(
false);
 
 
  152  _endSynchronize(
false);
 
 
  158void MeshMaterialVariableSynchronizerList::
 
  159_beginSynchronize(
bool is_blocking)
 
  161  if (m_p->m_is_in_sync)
 
  163  m_p->m_is_in_sync = 
true;
 
  165  m_p->m_total_size = 0;
 
  169  m_p->m_mat_env_sync_info = SyncInfo();
 
  170  m_p->m_env_only_sync_info = SyncInfo();
 
  173    SyncInfo& sync_info = m_p->m_mat_env_sync_info;
 
  174    _fillSyncInfo(sync_info);
 
  175    sync_info.mat_synchronizer = mm->
_internalApi()->allCellsMatEnvSynchronizer();
 
  176    sync_info.variables = m_p->m_mat_env_vars;
 
  177    sync_info.message_tag = MP::MessageTag(569);
 
  178    if (!sync_info.variables.empty()) {
 
  179      _beginSynchronizeMultiple(sync_info);
 
  181        _endSynchronizeMultiple2(sync_info);
 
  185    SyncInfo& sync_info = m_p->m_env_only_sync_info;
 
  186    _fillSyncInfo(sync_info);
 
  187    sync_info.mat_synchronizer = mm->
_internalApi()->allCellsEnvOnlySynchronizer();
 
  188    sync_info.variables = m_p->m_env_only_vars;
 
  189    sync_info.message_tag = MP::MessageTag(585);
 
  190    if (!sync_info.variables.empty()) {
 
  191      _beginSynchronizeMultiple(sync_info);
 
  193        _endSynchronizeMultiple2(sync_info);
 
  201void MeshMaterialVariableSynchronizerList::
 
  202_endSynchronize(
bool is_blocking)
 
  204  if (!m_p->m_is_in_sync)
 
  205    ARCANE_FATAL(
"beginSynchronize() has to be called before endSynchronize()");
 
  208    SyncInfo& sync_info = m_p->m_mat_env_sync_info;
 
  209    if (!sync_info.variables.empty() && !is_blocking)
 
  210      _endSynchronizeMultiple2(sync_info);
 
  211    m_p->m_total_size += sync_info.message_total_size;
 
  214    SyncInfo& sync_info = m_p->m_env_only_sync_info;
 
  215    if (!sync_info.variables.empty() && !is_blocking)
 
  216      _endSynchronizeMultiple2(sync_info);
 
  217    m_p->m_total_size += sync_info.message_total_size;
 
  220  m_p->m_is_in_sync = 
false;
 
  231    m_p->m_mat_env_vars.add(var);
 
  233    m_p->m_env_only_vars.add(var);
 
  236                 var->
name(), (
int)mvs);
 
 
  242void MeshMaterialVariableSynchronizerList::
 
  243_fillSyncInfo(SyncInfo& sync_info)
 
  245  sync_info.use_generic_version = m_p->m_use_generic_version;
 
  252void MeshMaterialVariableSynchronizerList::
 
  253_beginSynchronizeMultiple(SyncInfo& sync_info)
 
  257  const Int32 sync_version = sync_info.sync_version;
 
  259  if (sync_version == 8) {
 
  263  else if (sync_version == 7) {
 
  265    sync_info.buf_list = impl::makeOneBufferMeshMaterialSynchronizeBufferRef(mem);
 
  269    sync_info.buf_list = impl::makeMultiBufferMeshMaterialSynchronizeBufferRef(mem);
 
  271  if (sync_version < 8) {
 
  274    sync_info.buf_list->setNbRank(nb_rank);
 
  277  _beginSynchronizeMultiple2(sync_info);
 
  283void MeshMaterialVariableSynchronizerList::
 
  284_beginSynchronizeMultiple2(
SyncInfo& sync_info)
 
  286  ConstArrayView<MeshMaterialVariable*> vars = sync_info.variables;
 
  287  IMeshMaterialSynchronizeBuffer* buf_list = sync_info.buf_list.get();
 
  288  IMeshMaterialVariableSynchronizer* mmvs = sync_info.mat_synchronizer;
 
  304  if (!pm->isParallel())
 
  306  const bool use_new_version = sync_info.use_generic_version;
 
  307  RunQueue queue = pm->_internalApi()->queue();
 
  309  mmvs->checkRecompute();
 
  311  ITraceMng* tm = pm->traceMng();
 
  313  tm->info(4) << 
"MAT_SYNCHRONIZE version=" << sync_info.sync_version << 
" multiple n=" 
  314              << nb_var << 
" is_generic?=" << use_new_version;
 
  316  sync_info.data_sizes.resize(nb_var);
 
  318  for (
Integer i = 0; i < nb_var; ++i) {
 
  319    sync_info.data_sizes[i] = vars[i]->dataTypeSize();
 
  320    all_datatype_size += sync_info.data_sizes[i];
 
  321    tm->info(4) << 
"MAT_SYNCHRONIZE name=" << vars[i]->name()
 
  322                << 
" size=" << sync_info.data_sizes[i];
 
  329  for (
Integer i = 0; i < nb_rank; ++i) {
 
  330    ConstArrayView<MatVarIndex> ghost_matcells(mmvs->ghostItems(i));
 
  331    Integer total_ghost = ghost_matcells.size();
 
  332    buf_list->setReceiveBufferSize(i, total_ghost * all_datatype_size);
 
  333    ConstArrayView<MatVarIndex> shared_matcells(mmvs->sharedItems(i));
 
  334    Integer total_shared = shared_matcells.size();
 
  335    buf_list->setSendBufferSize(i, total_shared * all_datatype_size);
 
  337  buf_list->allocate();
 
  340  for (
Integer i = 0; i < nb_rank; ++i) {
 
  341    Int32 rank = ranks[i];
 
  342    MP::PointToPointMessageInfo msg_info(MP::MessageRank(rank), sync_info.message_tag, MP::eBlockingType::NonBlocking);
 
  343    sync_info.requests.add(
mpReceive(mpm, buf_list->receiveBuffer(i), msg_info));
 
  347  for (
Integer i = 0; i < nb_rank; ++i) {
 
  348    ConstArrayView<MatVarIndex> shared_matcells(mmvs->sharedItems(i));
 
  349    Integer total_shared = shared_matcells.size();
 
  352    for (
Integer z = 0; z < nb_var; ++z) {
 
  353      Integer my_data_size = sync_info.data_sizes[z];
 
  354      auto sub_view = values.subView(offset, total_shared * my_data_size);
 
  355      if (use_new_version) {
 
  356        auto* ptr = 
reinterpret_cast<std::byte*
>(sub_view.data());
 
  357        vars[z]->_internalApi()->copyToBuffer(shared_matcells, { ptr, sub_view.size() }, &queue);
 
  360        vars[z]->copyToBuffer(shared_matcells, sub_view);
 
  361      offset += total_shared * my_data_size;
 
  369  for (
Integer i = 0; i < nb_rank; ++i) {
 
  370    Int32 rank = ranks[i];
 
  371    MP::PointToPointMessageInfo msg_info(MP::MessageRank(rank), sync_info.message_tag, MP::eBlockingType::NonBlocking);
 
  372    sync_info.requests.add(
mpSend(mpm, buf_list->sendBuffer(i), msg_info));
 
  379void MeshMaterialVariableSynchronizerList::
 
  380_endSynchronizeMultiple2(
SyncInfo& sync_info)
 
  382  ConstArrayView<MeshMaterialVariable*> vars = sync_info.variables;
 
  383  IMeshMaterialVariableSynchronizer* mmvs = sync_info.mat_synchronizer;
 
  384  IVariableSynchronizer* var_syncer = mmvs->variableSynchronizer();
 
  385  IParallelMng* pm = var_syncer->parallelMng();
 
  387  if (!pm->isParallel())
 
  389  const bool use_new_version = sync_info.use_generic_version;
 
  390  RunQueue queue = pm->_internalApi()->queue();
 
  391  IMeshMaterialSynchronizeBuffer* buf_list = sync_info.buf_list.get();
 
  397  pm->waitAllRequests(sync_info.requests);
 
  400  for (
Integer i = 0; i < nb_rank; ++i) {
 
  401    ConstArrayView<MatVarIndex> ghost_matcells(mmvs->ghostItems(i));
 
  402    Integer total_ghost = ghost_matcells.size();
 
  406    for (
Integer z = 0; z < nb_var; ++z) {
 
  407      Integer my_data_size = sync_info.data_sizes[z];
 
  408      auto sub_view = values.subView(offset, total_ghost * my_data_size);
 
  409      if (use_new_version) {
 
  410        auto* ptr = 
reinterpret_cast<const std::byte*
>(sub_view.data());
 
  411        vars[z]->_internalApi()->copyFromBuffer(ghost_matcells, { ptr, sub_view.size() }, &queue);
 
  414        vars[z]->copyFromBuffer(ghost_matcells, sub_view);
 
  415      offset += total_ghost * my_data_size;
 
  418  sync_info.message_total_size += buf_list->totalSize();
 
#define ARCANE_THROW(exception_class,...)
Macro pour envoyer une exception avec formattage.
#define ARCANE_FATAL(...)
Macro envoyant une exception FatalErrorException.
Liste des fonctions d'échange de message.
constexpr Integer size() const noexcept
Nombre d'éléments du tableau.
virtual IMessagePassingMng * messagePassingMng() const =0
Gestionnaire de message de Arccore associé
virtual Int32ConstArrayView communicatingRanks()=0
Rangs des sous-domaines avec lesquels on communique.
virtual IParallelMng * parallelMng()=0
Gestionnaire parallèle associé
Interface du gestionnaire des matériaux et des milieux d'un maillage.
virtual Integer synchronizeVariableVersion() const =0
Version de l'implémentation pour la synchronisation des variables matériaux.
virtual IMeshMaterialMngInternal * _internalApi() const =0
API interne à Arcane.
virtual IVariableSynchronizer * variableSynchronizer()=0
Synchroniseur des variables classiques associé.
virtual eMemoryRessource bufferMemoryRessource() const =0
Ressource mémoire à utiliser pour les buffers de communication.
virtual Ref< IMeshMaterialSynchronizeBuffer > commonBuffer()=0
Buffer commun pour les messages.
Int64 totalMessageSize() const
Après appel à apply(), contient la taille des messages envoyés.
void beginSynchronize()
Commence une synchronisation non bloquante.
void apply()
Effectue la synchronisation.
void add(MeshMaterialVariable *var)
Ajoute la variable var à la liste des variables à synchroniser.
void endSynchronize()
Bloque tant que la synchronisation en cours n'est pas terminé.
String name() const override
Nom de la variable.
MatVarSpace space() const override
Espace de définition de la variable (matériau+milieu ou milieu uniquement)
Référence à une instance.
Vecteur 1D de données avec sémantique par valeur (style STL).
Active toujours les traces dans les parties Arcane concernant les matériaux.
MatVarSpace
Espace de définition d'une variable matériau.
@ Environment
Variable ayant des valeurs uniquement sur les milieux.
@ MaterialAndEnvironment
Variable ayant des valeurs sur les milieux et matériaux.
Request mpReceive(IMessagePassingMng *pm, ISerializer *values, const PointToPointMessageInfo &message)
Message de réception utilisant un ISerializer.
Request mpSend(IMessagePassingMng *pm, const ISerializer *values, const PointToPointMessageInfo &message)
Message d'envoi utilisant un ISerializer.
ArrayView< Byte > ByteArrayView
Equivalent C d'un tableau à une dimension de caractères.
std::int64_t Int64
Type entier signé sur 64 bits.
Int32 Integer
Type représentant un entier.
ConstArrayView< Int32 > Int32ConstArrayView
Equivalent C d'un tableau à une dimension d'entiers 32 bits.
Arcane::eMemoryResource eMemoryRessource
Typedef pour la version Arcane historique (avec 2's')
ConstArrayView< Byte > ByteConstArrayView
Equivalent C d'un tableau à une dimension de caractères.
std::int32_t Int32
Type entier signé sur 32 bits.
Espace de nommage contenant les types et déclarations qui gèrent le mécanisme de parallélisme par éch...