- Timestamp:
- 07/31/17 17:59:25 (7 years ago)
- Location:
- XIOS/dev/XIOS_DEV_CMIP6/src
- Files:
-
- 12 edited
Legend:
- Unmodified
- Added
- Removed
-
XIOS/dev/XIOS_DEV_CMIP6/src/context_client.cpp
r1201 r1232 35 35 else MPI_Comm_size(interComm, &serverSize); 36 36 37 computeLeader(clientRank, clientSize, serverSize, ranksServerLeader, ranksServerNotLeader); 38 39 timeLine = 0; 40 } 41 42 void CContextClient::computeLeader(int clientRank, int clientSize, int serverSize, 43 std::list<int>& rankRecvLeader, 44 std::list<int>& rankRecvNotLeader) 45 { 46 if ((0 == clientSize) || (0 == serverSize)) return; 47 37 48 if (clientSize < serverSize) 38 49 { … … 50 61 51 62 for (int i = 0; i < serverByClient; i++) 52 rank sServerLeader.push_back(rankStart + i);53 54 rank sServerNotLeader.resize(0);63 rankRecvLeader.push_back(rankStart + i); 64 65 rankRecvNotLeader.resize(0); 55 66 } 56 67 else … … 62 73 { 63 74 if (clientRank % (clientByServer + 1) == 0) 64 rank sServerLeader.push_back(clientRank / (clientByServer + 1));75 rankRecvLeader.push_back(clientRank / (clientByServer + 1)); 65 76 else 66 rank sServerNotLeader.push_back(clientRank / (clientByServer + 1));77 rankRecvNotLeader.push_back(clientRank / (clientByServer + 1)); 67 78 } 68 79 else … … 70 81 int rank = clientRank - (clientByServer + 1) * remain; 71 82 if (rank % clientByServer == 0) 72 rank sServerLeader.push_back(remain + rank / clientByServer);83 rankRecvLeader.push_back(remain + rank / clientByServer); 73 84 else 74 ranksServerNotLeader.push_back(remain + rank / clientByServer); 75 } 76 } 77 78 timeLine = 0; 85 rankRecvNotLeader.push_back(remain + rank / clientByServer); 86 } 87 } 79 88 } 80 89 -
XIOS/dev/XIOS_DEV_CMIP6/src/context_client.hpp
r1201 r1232 49 49 bool isAttachedModeEnabled() const; 50 50 bool hasTemporarilyBufferedEvent() const { return !tmpBufferedEvent.isEmpty(); }; 51 52 static void computeLeader(int clientRank, int clientSize, int serverSize, 53 std::list<int>& rankRecvLeader, 54 std::list<int>& rankRecvNotLeader); 51 55 52 56 // Close and finalize context client -
XIOS/dev/XIOS_DEV_CMIP6/src/node/context.cpp
r1227 r1232 477 477 finalized = true; 478 478 479 closeAllFile(); // Just move to here to make sure that server-level 1 can close files 479 480 if (hasServer && !hasClient) 480 { 481 closeAllFile(); 481 { 482 482 registryOut->hierarchicalGatherRegistry() ; 483 483 if (server->intraCommRank==0) CXios::globalRegistry->mergeRegistry(*registryOut) ; … … 525 525 526 526 // Check grid and calculate its distribution 527 checkGridEnabledFields(); 528 527 checkGridEnabledFields(); 528 529 529 // Distribute files between secondary servers according to the data size 530 530 distributeFiles(); … … 548 548 // We have enough information to send to server 549 549 // First of all, send all enabled files 550 sendEnabledFiles(); 551 552 // Then, send all enabled fields 553 sendEnabledFields(); 550 sendEnabledFiles(this->enabledWriteModeFiles); 551 // We only use server-level 1 (for now) to read data 552 if (!hasServer) 553 sendEnabledFiles(this->enabledReadModeFiles); 554 555 // Then, send all enabled fields 556 sendEnabledFieldsInFiles(this->enabledWriteModeFiles); 557 if (!hasServer) 558 sendEnabledFieldsInFiles(this->enabledReadModeFiles); 554 559 555 560 // At last, we have all info of domain and axis, then send them 556 sendRefDomainsAxis(); 561 sendRefDomainsAxisScalars(this->enabledWriteModeFiles); 562 if (!hasServer) 563 sendRefDomainsAxisScalars(this->enabledReadModeFiles); 557 564 558 565 // After that, send all grid (if any) 559 sendRefGrid(); 566 sendRefGrid(this->enabledWriteModeFiles); 567 if (!hasServer) 568 sendRefGrid(this->enabledReadModeFiles); 560 569 561 570 // We have a xml tree on the server side and now, it should be also processed 562 571 sendPostProcessing(); 563 564 sendGridEnabledFields(); 572 573 sendGridEnabledFieldsInFiles(this->enabledWriteModeFiles); 574 if (!hasServer) 575 sendGridEnabledFieldsInFiles(this->enabledReadModeFiles); 565 576 } 566 577 allProcessed = true; … … 630 641 } 631 642 632 checkGridEnabledFields(); 643 checkGridEnabledFields(); 633 644 634 645 if (hasClient) this->sendProcessingGridOfEnabledFields(); … … 646 657 } 647 658 648 void CContext::findAllEnabledFields(void) 649 { 650 for (unsigned int i = 0; i < this->enabledFiles.size(); i++) 651 (void)this->enabledFiles[i]->getEnabledFields(); 652 } 653 654 void CContext::findAllEnabledFieldsInReadModeFiles(void) 655 { 656 for (unsigned int i = 0; i < this->enabledReadModeFiles.size(); ++i) 657 (void)this->enabledReadModeFiles[i]->getEnabledFields(); 659 void CContext::findAllEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles) 660 { 661 for (unsigned int i = 0; i < activeFiles.size(); i++) 662 (void)activeFiles[i]->getEnabledFields(); 658 663 } 659 664 … … 664 669 } 665 670 666 void CContext::sendGridEnabledFields() 671 /*! 672 Send active (enabled) fields in file from a client to others 673 \param [in] activeFiles files contains enabled fields to send 674 */ 675 void CContext::sendGridEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles) 676 { 677 int size = activeFiles.size(); 678 for (int i = 0; i < size; ++i) 679 { 680 activeFiles[i]->sendGridOfEnabledFields(); 681 } 682 } 683 684 void CContext::checkGridEnabledFields() 685 { 686 int size = enabledFiles.size(); 687 for (int i = 0; i < size; ++i) 688 { 689 enabledFiles[i]->checkGridOfEnabledFields(); 690 } 691 } 692 693 /*! 694 Check grid of active (enabled) fields in file 695 \param [in] activeFiles files contains enabled fields whose grid needs checking 696 */ 697 void CContext::checkGridEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles) 698 { 699 int size = activeFiles.size(); 700 for (int i = 0; i < size; ++i) 701 { 702 activeFiles[i]->checkGridOfEnabledFields(); 703 } 704 } 705 706 /*! 707 Go up the hierachical tree via field_ref and do check of attributes of fields 708 This can be done in a client then all computed information will be sent from this client to others 709 \param [in] sendToServer Flag to indicate whether calculated information will be sent 710 */ 711 void CContext::solveOnlyRefOfEnabledFields(bool sendToServer) 667 712 { 668 713 int size = this->enabledFiles.size(); 669 714 for (int i = 0; i < size; ++i) 670 { 671 this->enabledFiles[i]->sendGridOfEnabledFields(); 672 } 673 } 674 675 void CContext::checkGridEnabledFields() 676 { 677 int size = this->enabledFiles.size(); 715 { 716 this->enabledFiles[i]->solveOnlyRefOfEnabledFields(sendToServer); 717 } 718 678 719 for (int i = 0; i < size; ++i) 679 720 { 680 this->enabledFiles[i]->checkGridOfEnabledFields();681 }682 }683 684 void CContext::solveOnlyRefOfEnabledFields(bool sendToServer)685 {686 int size = this->enabledFiles.size();687 for (int i = 0; i < size; ++i)688 {689 this->enabledFiles[i]->solveOnlyRefOfEnabledFields(sendToServer);690 }691 692 for (int i = 0; i < size; ++i)693 {694 721 this->enabledFiles[i]->generateNewTransformationGridDest(); 695 722 } 696 723 } 697 724 725 /*! 726 Go up the hierachical tree via field_ref and do check of attributes of fields. 727 The transformation can be done in this step. 728 All computed information will be sent from this client to others. 729 \param [in] sendToServer Flag to indicate whether calculated information will be sent 730 */ 698 731 void CContext::solveAllRefOfEnabledFieldsAndTransform(bool sendToServer) 699 732 { … … 831 864 832 865 // (1) Find all enabled files in write mode 833 for (int i = 0; i < this->enabledFiles.size(); ++i)834 {835 if (enabledFiles[i]->mode.isEmpty() || (!enabledFiles[i]->mode.isEmpty() && enabledFiles[i]->mode.getValue() == CFile::mode_attr::write ))836 enabledWriteModeFiles.push_back(enabledFiles[i]);837 }866 // for (int i = 0; i < this->enabledFiles.size(); ++i) 867 // { 868 // if (enabledFiles[i]->mode.isEmpty() || (!enabledFiles[i]->mode.isEmpty() && enabledFiles[i]->mode.getValue() == CFile::mode_attr::write )) 869 // enabledWriteModeFiles.push_back(enabledFiles[i]); 870 // } 838 871 839 872 // (2) Estimate the data volume for each file … … 882 915 883 916 for (int i = 0; i < this->enabledReadModeFiles.size(); ++i) 884 enabledReadModeFiles[i]->setContextClient(client); 917 { 918 enabledReadModeFiles[i]->setContextClient(client); 919 } 885 920 } 886 921 else … … 891 926 } 892 927 928 /*! 929 Find all files in write mode 930 */ 931 void CContext::findEnabledWriteModeFiles(void) 932 { 933 int size = this->enabledFiles.size(); 934 for (int i = 0; i < size; ++i) 935 { 936 if (enabledFiles[i]->mode.isEmpty() || 937 (!enabledFiles[i]->mode.isEmpty() && enabledFiles[i]->mode.getValue() == CFile::mode_attr::write )) 938 enabledWriteModeFiles.push_back(enabledFiles[i]); 939 } 940 } 941 942 /*! 943 Find all files in read mode 944 */ 893 945 void CContext::findEnabledReadModeFiles(void) 894 946 { … … 1217 1269 1218 1270 //Initialisation du vecteur 'enabledFiles' contenant la liste des fichiers à sortir. 1219 this->findEnabledFiles(); 1220 1271 findEnabledFiles(); 1272 findEnabledWriteModeFiles(); 1273 findEnabledReadModeFiles(); 1274 1221 1275 // For now, only read files with client and only one level server 1222 if (hasClient && !hasServer) this->findEnabledReadModeFiles(); 1223 1224 // Find all enabled fields of each file 1225 this->findAllEnabledFields(); 1276 // if (hasClient && !hasServer) findEnabledReadModeFiles(); 1277 1278 // Find all enabled fields of each file 1279 findAllEnabledFieldsInFiles(this->enabledWriteModeFiles); 1280 findAllEnabledFieldsInFiles(this->enabledReadModeFiles); 1281 1226 1282 // For now, only read files with client and only one level server 1227 if (hasClient && !hasServer) this->findAllEnabledFieldsInReadModeFiles();1228 1283 // if (hasClient && !hasServer) 1284 // findAllEnabledFieldsInFiles(this->enabledReadModeFiles); 1229 1285 1230 1286 if (hasClient && !hasServer) 1231 1287 { 1232 // Try to read attributes of fields in file then fill in corresponding grid (or domain, axis) 1233 this->readAttributesOfEnabledFieldsInReadModeFiles(); 1288 initReadFiles(); 1289 // Try to read attributes of fields in file then fill in corresponding grid (or domain, axis) 1290 this->readAttributesOfEnabledFieldsInReadModeFiles(); 1234 1291 } 1235 1292 … … 1259 1316 if (hasClient) 1260 1317 { 1261 size_t numEnabledFiles = this->enabled Files.size();1318 size_t numEnabledFiles = this->enabledWriteModeFiles.size(); 1262 1319 for (size_t i = 0; i < numEnabledFiles; ++i) 1263 1320 { 1264 CFile* file = this->enabled Files[i];1321 CFile* file = this->enabledWriteModeFiles[i]; 1265 1322 // if (file->getContextClient() == contextClient) 1266 1323 { … … 1280 1337 if (maxEventSize[it->first] < it->second) 1281 1338 maxEventSize[it->first] = it->second; 1339 } 1340 } 1341 } 1342 } 1343 1344 // Not a good approach here, duplicate code 1345 if (!hasServer) 1346 { 1347 size_t numEnabledFiles = this->enabledReadModeFiles.size(); 1348 for (size_t i = 0; i < numEnabledFiles; ++i) 1349 { 1350 CFile* file = this->enabledReadModeFiles[i]; 1351 { 1352 std::vector<CField*> enabledFields = file->getEnabledFields(); 1353 size_t numEnabledFields = enabledFields.size(); 1354 for (size_t j = 0; j < numEnabledFields; ++j) 1355 { 1356 const std::map<int, StdSize> mapSize = enabledFields[j]->getGridAttributesBufferSize(); 1357 std::map<int, StdSize>::const_iterator it = mapSize.begin(), itE = mapSize.end(); 1358 for (; it != itE; ++it) 1359 { 1360 // If attributesSize[it->first] does not exist, it will be zero-initialized 1361 // so we can use it safely without checking for its existance 1362 if (attributesSize[it->first] < it->second) 1363 attributesSize[it->first] = it->second; 1364 1365 if (maxEventSize[it->first] < it->second) 1366 maxEventSize[it->first] = it->second; 1367 } 1282 1368 } 1283 1369 } … … 1341 1427 1342 1428 //! Client side: Send infomation of active files (files are enabled to write out) 1343 void CContext::sendEnabledFiles( )1344 { 1345 int size = this->enabledFiles.size();1429 void CContext::sendEnabledFiles(const std::vector<CFile*>& activeFiles) 1430 { 1431 int size = activeFiles.size(); 1346 1432 1347 1433 // In a context, each type has a root definition, e.g: axis, domain, field. … … 1353 1439 for (int i = 0; i < size; ++i) 1354 1440 { 1355 cfgrpPtr->sendCreateChild(this->enabledFiles[i]->getId(),enabledFiles[i]->getContextClient()); 1356 this->enabledFiles[i]->sendAllAttributesToServer(enabledFiles[i]->getContextClient()); 1357 this->enabledFiles[i]->sendAddAllVariables(enabledFiles[i]->getContextClient()); 1441 CFile* f = activeFiles[i]; 1442 cfgrpPtr->sendCreateChild(f->getId(),f->getContextClient()); 1443 f->sendAllAttributesToServer(f->getContextClient()); 1444 f->sendAddAllVariables(f->getContextClient()); 1358 1445 } 1359 1446 } 1360 1447 1361 1448 //! Client side: Send information of active fields (ones are written onto files) 1362 void CContext::sendEnabledFields ()1363 { 1364 int size = this->enabledFiles.size();1449 void CContext::sendEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles) 1450 { 1451 int size = activeFiles.size(); 1365 1452 for (int i = 0; i < size; ++i) 1366 1453 { 1367 this->enabledFiles[i]->sendEnabledFields(enabledFiles[i]->getContextClient());1454 activeFiles[i]->sendEnabledFields(activeFiles[i]->getContextClient()); 1368 1455 } 1369 1456 } … … 1488 1575 1489 1576 //! Client side: Send information of reference grid of active fields 1490 void CContext::sendRefGrid( )1577 void CContext::sendRefGrid(const std::vector<CFile*>& activeFiles) 1491 1578 { 1492 1579 std::set<StdString> gridIds; 1493 int sizeFile = this->enabledFiles.size();1580 int sizeFile = activeFiles.size(); 1494 1581 CFile* filePtr(NULL); 1495 1582 … … 1497 1584 for (int i = 0; i < sizeFile; ++i) 1498 1585 { 1499 filePtr = this->enabledFiles[i];1586 filePtr = activeFiles[i]; 1500 1587 std::vector<CField*> enabledFields = filePtr->getEnabledFields(); 1501 1588 int sizeField = enabledFields.size(); … … 1521 1608 } 1522 1609 1523 1524 //! Client side: Send information of reference domain and axis of active fields 1525 void CContext::sendRefDomainsAxis() 1610 //! Client side: Send information of reference domain, axis and scalar of active fields 1611 void CContext::sendRefDomainsAxisScalars(const std::vector<CFile*>& activeFiles) 1526 1612 { 1527 1613 std::set<StdString> domainIds, axisIds, scalarIds; 1528 1614 1529 1615 // Find all reference domain and axis of all active fields 1530 int numEnabledFiles = this->enabledFiles.size();1616 int numEnabledFiles = activeFiles.size(); 1531 1617 for (int i = 0; i < numEnabledFiles; ++i) 1532 1618 { 1533 std::vector<CField*> enabledFields = this->enabledFiles[i]->getEnabledFields();1619 std::vector<CField*> enabledFields = activeFiles[i]->getEnabledFields(); 1534 1620 int numEnabledFields = enabledFields.size(); 1535 1621 for (int j = 0; j < numEnabledFields; ++j) … … 1592 1678 info(50) << " Current memory used by XIOS : "<< MemTrack::getCurrentMemorySize()*1.0/(1024*1024)<<" Mbyte, at timestep "<<step<<" of context "<<this->getId()<<endl ; 1593 1679 #endif 1594 if (hasClient) 1680 //if (hasClient) 1681 if (hasClient && !hasServer) // For now we only use server level 1 to read data 1595 1682 { 1596 1683 checkPrefetchingOfEnabledReadModeFiles(); … … 1599 1686 } 1600 1687 1688 void CContext::initReadFiles(void) 1689 { 1690 vector<CFile*>::const_iterator it; 1691 1692 for (it=enabledReadModeFiles.begin(); it != enabledReadModeFiles.end(); it++) 1693 { 1694 (*it)->initRead(); 1695 } 1696 } 1697 1601 1698 //! Server side: Create header of netcdf file 1602 void CContext::createFileHeader(void 1699 void CContext::createFileHeader(void) 1603 1700 { 1604 1701 vector<CFile*>::const_iterator it; 1605 1702 1606 1703 for (it=enabledFiles.begin(); it != enabledFiles.end(); it++) 1704 // for (it=enabledWriteModeFiles.begin(); it != enabledWriteModeFiles.end(); it++) 1607 1705 { 1608 (*it)->init File();1706 (*it)->initWrite(); 1609 1707 } 1610 1708 } -
XIOS/dev/XIOS_DEV_CMIP6/src/node/context.hpp
r1212 r1232 104 104 105 105 // Some functions to process context 106 void findAllEnabledFields(void); 107 void findAllEnabledFieldsInReadModeFiles(void); 106 void findAllEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles); 107 // void findAllEnabledFields(void); 108 // void findAllEnabledFieldsInReadModeFiles(void); 108 109 void readAttributesOfEnabledFieldsInReadModeFiles(); 109 110 void solveAllInheritance(bool apply=true); 110 111 void findEnabledFiles(void); 112 void findEnabledWriteModeFiles(void); 111 113 void findEnabledReadModeFiles(void); 112 114 void closeAllFile(void); 113 115 void updateCalendar(int step); 114 void createFileHeader(void ); 116 void createFileHeader(void); 117 void initReadFiles(void); 115 118 void checkAxisDomainsGridsEligibilityForCompressedOutput(); 116 119 void prepareTimeseries(void); … … 127 130 void solveAllRefOfEnabledFieldsAndTransform(bool sendToServer); 128 131 void checkGridEnabledFields(); 129 void sendGridEnabledFields(); 132 void checkGridEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles); 133 void sendGridEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles); 130 134 131 135 // std::map<int, StdSize> getAttributesBufferSize(std::map<int, StdSize>& maxEventSize); … … 144 148 void sendUpdateCalendar(int step); 145 149 void sendCreateFileHeader(void); 146 void sendEnabledFiles( );147 void sendEnabledFields ();148 void sendRefDomainsAxis ();149 void sendRefGrid( );150 void sendEnabledFiles(const std::vector<CFile*>& activeFiles); 151 void sendEnabledFieldsInFiles(const std::vector<CFile*>& activeFiles); 152 void sendRefDomainsAxisScalars(const std::vector<CFile*>& activeFiles); 153 void sendRefGrid(const std::vector<CFile*>& activeFiles); 150 154 void sendPostProcessing(); 151 155 void sendPostProcessingGlobalAttributes(); -
XIOS/dev/XIOS_DEV_CMIP6/src/node/domain.cpp
r1223 r1232 1810 1810 } 1811 1811 1812 // Even if servers have no index, they must received something from client 1813 // We only use several client to send "empty" message to these servers 1812 1814 CServerDistributionDescription serverDescription(nGlobDomain, nbServer); 1813 if (isUnstructed_) serverDescription.computeServerGlobalIndexInRange(std::make_pair<size_t,size_t>(indexBegin, indexEnd), 0); 1814 else serverDescription.computeServerGlobalIndexInRange(std::make_pair<size_t,size_t>(indexBegin, indexEnd), 1); 1815 std::vector<int> serverZeroIndex; 1816 if (isUnstructed_) serverZeroIndex = serverDescription.computeServerGlobalIndexInRange(std::make_pair<size_t,size_t>(indexBegin, indexEnd), 0); 1817 else serverZeroIndex = serverDescription.computeServerGlobalIndexInRange(std::make_pair<size_t,size_t>(indexBegin, indexEnd), 1); 1818 1819 std::list<int> serverZeroIndexLeader; 1820 std::list<int> serverZeroIndexNotLeader; 1821 CContextClient::computeLeader(client->clientRank, client->clientSize, serverZeroIndex.size(), serverZeroIndexLeader, serverZeroIndexNotLeader); 1822 for (std::list<int>::iterator it = serverZeroIndexLeader.begin(); it != serverZeroIndexLeader.end(); ++it) 1823 *it = serverZeroIndex[*it]; 1815 1824 1816 1825 CClientServerMapping* clientServerMap = new CClientServerMappingDistributed(serverDescription.getGlobalIndexRange(), … … 1821 1830 CClientServerMapping::GlobalIndexMap::const_iterator it = globalIndexDomainOnServer.begin(), 1822 1831 ite = globalIndexDomainOnServer.end(); 1832 indSrv_.swap(globalIndexDomainOnServer); 1823 1833 connectedServerRank_.clear(); 1824 for (it = globalIndexDomainOnServer.begin(); it != ite; ++it) {1834 for (it = indSrv_.begin(); it != ite; ++it) 1825 1835 connectedServerRank_.push_back(it->first); 1826 } 1827 1828 indSrv_.swap(globalIndexDomainOnServer); 1836 1837 for (std::list<int>::const_iterator it = serverZeroIndexLeader.begin(); it != serverZeroIndexLeader.end(); ++it) 1838 connectedServerRank_.push_back(*it); 1839 1840 // Even if a client has no index, it must connect to at least one server and 1841 // send an "empty" data to this server 1842 if (connectedServerRank_.empty()) 1843 connectedServerRank_.push_back(client->clientRank % client->serverSize); 1844 1829 1845 nbConnectedClients_ = clientServerMap->computeConnectedClients(client->serverSize, client->clientSize, client->intraComm, connectedServerRank_); 1830 1846 1831 clientServerMap->computeServerIndexMapping(globalIndexDomainZoom);1832 CClientServerMapping::GlobalIndexMap& globalIndexDomainZoomOnServer = clientServerMap->getGlobalIndexOnServer();1833 indZoomSrv_.swap(globalIndexDomainZoomOnServer);1847 // clientServerMap->computeServerIndexMapping(globalIndexDomainZoom); 1848 // CClientServerMapping::GlobalIndexMap& globalIndexDomainZoomOnServer = clientServerMap->getGlobalIndexOnServer(); 1849 // indZoomSrv_.swap(globalIndexDomainZoomOnServer); 1834 1850 1835 for (it = indZoomSrv_.begin(); it != indZoomSrv_.end(); ++it)1836 connectedServerZoomRank_.push_back(it->first);1837 1838 nbConnectedClientsZoom_ = clientServerMap->computeConnectedClients(client->serverSize, client->clientSize, client->intraComm, connectedServerZoomRank_);1851 // for (it = indZoomSrv_.begin(); it != indZoomSrv_.end(); ++it) 1852 // connectedServerZoomRank_.push_back(it->first); 1853 1854 // nbConnectedClientsZoom_ = clientServerMap->computeConnectedClients(client->serverSize, client->clientSize, client->intraComm, connectedServerZoomRank_); 1839 1855 1840 1856 delete clientServerMap; … … 2007 2023 This function can be used in the future??? 2008 2024 */ 2009 void CDomain::sendIndexZoom()2010 {2011 int ns, n, i, j, ind, nv, idx;2012 CContext* context = CContext::getCurrent();2013 2014 // int nbSrvPools = (context->hasServer) ? context->clientPrimServer.size() : 1;2015 int nbSrvPools = (context->hasServer) ? (context->hasClient ? context->clientPrimServer.size() : 0) : 1;2016 for (int p = 0; p < nbSrvPools; ++p)2017 {2018 CContextClient* client = (0 != context->clientPrimServer.size()) ? context->clientPrimServer[p] : context->client;2019 CEventClient eventIndexZoom(getType(), EVENT_ID_INDEX_ZOOM);2020 2021 list<CMessage> list_msgsIndex;2022 list<CArray<int,1> > list_indZoom;2023 2024 boost::unordered_map<int, vector<size_t> >::const_iterator itZoom, iteZoom;2025 iteZoom = indZoomSrv_.end();2026 for (int k = 0; k < connectedServerZoomRank_.size(); ++k)2027 {2028 int nbIndGlob = 0;2029 int rank = connectedServerZoomRank_[k];2030 int nbIndZoom = 0;2031 itZoom = indZoomSrv_.find(rank);2032 if (iteZoom != itZoom)2033 nbIndZoom = itZoom->second.size();2025 // void CDomain::sendIndexZoom() 2026 // { 2027 // int ns, n, i, j, ind, nv, idx; 2028 // CContext* context = CContext::getCurrent(); 2029 2030 // // int nbSrvPools = (context->hasServer) ? context->clientPrimServer.size() : 1; 2031 // int nbSrvPools = (context->hasServer) ? (context->hasClient ? context->clientPrimServer.size() : 0) : 1; 2032 // for (int p = 0; p < nbSrvPools; ++p) 2033 // { 2034 // CContextClient* client = (0 != context->clientPrimServer.size()) ? context->clientPrimServer[p] : context->client; 2035 // CEventClient eventIndexZoom(getType(), EVENT_ID_INDEX_ZOOM); 2036 2037 // list<CMessage> list_msgsIndex; 2038 // list<CArray<int,1> > list_indZoom; 2039 2040 // boost::unordered_map<int, vector<size_t> >::const_iterator itZoom, iteZoom; 2041 // iteZoom = indZoomSrv_.end(); 2042 // for (int k = 0; k < connectedServerZoomRank_.size(); ++k) 2043 // { 2044 // int nbIndGlob = 0; 2045 // int rank = connectedServerZoomRank_[k]; 2046 // int nbIndZoom = 0; 2047 // itZoom = indZoomSrv_.find(rank); 2048 // if (iteZoom != itZoom) 2049 // nbIndZoom = itZoom->second.size(); 2034 2050 2035 list_indZoom.push_back(CArray<int,1>(nbIndZoom));2036 CArray<int,1>& indZoom = list_indZoom.back();2037 for (n = 0; n < nbIndZoom; ++n)2038 {2039 indZoom(n) = static_cast<int>(itZoom->second[n]);2040 }2041 2042 list_msgsIndex.push_back(CMessage());2043 list_msgsIndex.back() << this->getId(); // enum ne fonctionne pour les message => ToFix2044 list_msgsIndex.back() << list_indZoom.back() << doZoomByIndex_; //list_indi.back() << list_indj.back2045 2046 eventIndexZoom.push(rank, nbConnectedClientsZoom_[rank], list_msgsIndex.back());2047 }2048 2049 client->sendEvent(eventIndexZoom);2050 }2051 }2051 // list_indZoom.push_back(CArray<int,1>(nbIndZoom)); 2052 // CArray<int,1>& indZoom = list_indZoom.back(); 2053 // for (n = 0; n < nbIndZoom; ++n) 2054 // { 2055 // indZoom(n) = static_cast<int>(itZoom->second[n]); 2056 // } 2057 2058 // list_msgsIndex.push_back(CMessage()); 2059 // list_msgsIndex.back() << this->getId(); // enum ne fonctionne pour les message => ToFix 2060 // list_msgsIndex.back() << list_indZoom.back() << doZoomByIndex_; //list_indi.back() << list_indj.back 2061 2062 // eventIndexZoom.push(rank, nbConnectedClientsZoom_[rank], list_msgsIndex.back()); 2063 // } 2064 2065 // client->sendEvent(eventIndexZoom); 2066 // } 2067 // } 2052 2068 2053 2069 /*! … … 2673 2689 { 2674 2690 lInd = globalLocalIndexMap_[size_t(tmpInd(ind))]; 2675 if (!mask_1d(lInd)) 2676 mask_1d(lInd) = tmp(ind);2691 if (!mask_1d(lInd)) // Only rewrite mask_1d if it's not true 2692 mask_1d(lInd) = tmp(ind); 2677 2693 } 2678 2694 } -
XIOS/dev/XIOS_DEV_CMIP6/src/node/field.cpp
r1215 r1232 41 41 , hasTimeCentered(false) 42 42 , wasDataAlreadyReceivedFromServer(false) 43 , isEOF(false) 43 , isEOF(false), nstepMaxRead(false) 44 44 { setVirtualVariableGroup(CVariableGroup::create(getId() + "_virtual_variable_group")); } 45 45 … … 56 56 , hasTimeCentered(false) 57 57 , wasDataAlreadyReceivedFromServer(false) 58 , isEOF(false) 58 , isEOF(false), nstepMaxRead(false) 59 59 { setVirtualVariableGroup(CVariableGroup::create(getId() + "_virtual_variable_group")); } 60 60 … … 262 262 void CField::writeField(void) 263 263 { 264 if (!getRelFile()-> allDomainEmpty)264 if (!getRelFile()->isEmptyZone()) 265 265 { 266 266 if (grid->doGridHaveDataToWrite() || getRelFile()->type == CFile::type_attr::one_file) … … 273 273 } 274 274 275 /* 276 Send a request for reading data. 277 Client sends a request to server for demanding server to read data and send back to it. 278 For now, this function is called only by client 279 In the future, it can be called by level-1 servers 280 \param [in] tsDataRequested timestamp when the call is made 281 */ 275 282 bool CField::sendReadDataRequest(const CDate& tsDataRequested) 276 283 { 277 284 CContext* context = CContext::getCurrent(); 278 // CContextClient* client = context->client; 285 // CContextClient* client = context->client; 286 287 // This code is for future: If we want to read file with level-2 servers 279 288 CContextClient* client = (!context->hasServer) ? context->client : this->file->getContextClient(); 280 289 … … 332 341 } 333 342 343 /*! 344 Receive data request sent from client and process it 345 Every time server receives this request, it will try to read data and sent read data back to client 346 At the moment, this function is called by server level 1 347 In the future, this should (only) be done by the last level servers. 348 */ 334 349 void CField::recvReadDataRequest(void) 335 350 { 336 351 CContext* context = CContext::getCurrent(); 337 352 CContextClient* client = context->client; 338 // CContextClient* client = (!context->hasServer) ? context->client : this->file->getContextClient();339 353 340 354 CEventClient event(getType(), EVENT_ID_READ_DATA_READY); 341 355 std::list<CMessage> msgs; 342 356 343 boolhasData = readField();357 EReadField hasData = readField(); 344 358 345 359 map<int, CArray<double,1> >::iterator it; … … 356 370 CMessage& msg = msgs.back(); 357 371 msg << getId(); 358 if (hasData) 359 msg << getNStep() - 1 << recvDataSrv; 360 else 361 msg << int(-1); 372 switch (hasData) 373 { 374 case RF_DATA: 375 msg << getNStep() - 1 << recvDataSrv; 376 break; 377 case RF_NODATA: 378 msg << int(-2); 379 break; 380 case RF_EOF: 381 default: 382 msg << int(-1); 383 break; 384 } 385 362 386 event.push(*itRank, 1, msg); 363 387 } … … 385 409 CMessage& msg = msgs.back(); 386 410 msg << getId(); 387 if (hasData) 388 msg << getNStep() - 1 << tmp; 389 else 390 msg << int(-1); 411 switch (hasData) 412 { 413 case RF_DATA: 414 msg << getNStep() - 1 << tmp; 415 break; 416 case RF_NODATA: 417 msg << int(-2) << tmp; 418 break; 419 case RF_EOF: 420 default: 421 msg << int(-1); 422 break; 423 } 424 391 425 event.push(it->first, grid->nbReadSenders[0][it->first], msg); 392 426 } … … 395 429 } 396 430 397 bool CField::readField(void) 431 /*! 432 Read field from a file. 433 A field is read with the distribution of data on the server side 434 \return State of field can be read from a file 435 */ 436 CField::EReadField CField::readField(void) 398 437 { 438 CContext* context = CContext::getCurrent(); 399 439 grid->computeWrittenIndex(); 400 if (!getRelFile()->allDomainEmpty) 401 { 402 if (grid->doGridHaveDataToWrite() || getRelFile()->type == CFile::type_attr::one_file) 440 getRelFile()->initRead(); 441 EReadField readState = RF_DATA; 442 443 if (!getRelFile()->isEmptyZone()) 444 { 445 if (grid->doGridHaveDataToWrite() || getRelFile()->type == CFile::type_attr::one_file) 403 446 { 404 447 if (0 == recvDataSrv.numElements()) … … 407 450 recvDataSrv.resize(storeClient.numElements()); 408 451 } 409 452 410 453 getRelFile()->checkReadFile(); 454 411 455 if (!nstepMax) 412 456 { … … 417 461 418 462 if (getNStep() > nstepMax && (getRelFile()->cyclic.isEmpty() || !getRelFile()->cyclic) ) 419 return false; 420 421 getRelFile()->getDataInput()->readFieldData(CField::get(this)); 422 } 423 } 424 425 return true; 463 readState = RF_EOF; 464 465 if (RF_EOF != readState) 466 getRelFile()->getDataInput()->readFieldData(CField::get(this)); 467 } 468 } 469 else 470 { 471 this->incrementNStep(); 472 if (getNStep() > nstepMax && (getRelFile()->cyclic.isEmpty() || !getRelFile()->cyclic) ) 473 readState = RF_EOF; 474 else 475 readState = RF_NODATA; 476 477 if (!nstepMaxRead) // This can be a bug if we try to read field from zero time record 478 readState = RF_NODATA; 479 } 480 481 if (!nstepMaxRead) 482 { 483 MPI_Allreduce(&nstepMax, &nstepMax, 1, MPI_INT, MPI_MAX, context->server->intraComm); 484 nstepMaxRead = true; 485 } 486 487 return readState; 426 488 } 427 489 490 /* 491 Receive read data from server. 492 At the moment, this function is called in the client side. 493 In the future, this function can be called hiearachically (server n-1, server n -2, ..., client) 494 \param event event containing read data 495 */ 428 496 void CField::recvReadDataReady(CEventServer& event) 429 497 { … … 443 511 } 444 512 513 /*! 514 Receive read data from server 515 \param [in] ranks Ranks of sending processes 516 \param [in] buffers buffers containing read data 517 */ 445 518 void CField::recvReadDataReady(vector<int> ranks, vector<CBufferIn*> buffers) 446 519 { … … 528 601 { 529 602 this->nstepMax = 0; 603 nstepMaxRead = false; 530 604 } 531 605 -
XIOS/dev/XIOS_DEV_CMIP6/src/node/field.hpp
r1215 r1232 58 58 typedef CFieldAttributes SuperClassAttribute; 59 59 60 enum EReadField 61 { 62 RF_NODATA, RF_EOF, RF_DATA 63 }; 64 60 65 public: 61 66 … … 157 162 static void recvReadDataRequest(CEventServer& event); 158 163 void recvReadDataRequest(void); 159 boolreadField(void);164 EReadField readField(void); 160 165 static void recvReadDataReady(CEventServer& event); 161 166 void recvReadDataReady(vector<int> ranks, vector<CBufferIn*> buffers); … … 230 235 bool isReferenceSolved; 231 236 bool isReferenceSolvedAndTransformed; 237 bool nstepMaxRead; 232 238 233 239 private: -
XIOS/dev/XIOS_DEV_CMIP6/src/node/file.cpp
r1201 r1232 25 25 : CObjectTemplate<CFile>(), CFileAttributes() 26 26 , vFieldGroup(), data_out(), enabledFields(), fileComm(MPI_COMM_NULL) 27 , allDomainEmpty(false), isOpen(false)27 , isOpen(false), read_client(0), checkRead(false), allZoneEmpty(false) 28 28 { 29 29 setVirtualFieldGroup(CFieldGroup::create(getId() + "_virtual_field_group")); … … 34 34 : CObjectTemplate<CFile>(id), CFileAttributes() 35 35 , vFieldGroup(), data_out(), enabledFields(), fileComm(MPI_COMM_NULL) 36 , allDomainEmpty(false), isOpen(false)36 , isOpen(false), read_client(0), checkRead(false), allZoneEmpty(false) 37 37 { 38 38 setVirtualFieldGroup(CFieldGroup::create(getId() + "_virtual_field_group")); … … 207 207 208 208 //! Initialize a file in order to write into it 209 void CFile::init File(void)209 void CFile::initWrite(void) 210 210 { 211 211 CContext* context = CContext::getCurrent(); … … 228 228 } 229 229 } 230 isOpen = false; 231 232 allDomainEmpty = true; 230 isOpen = false; 233 231 234 232 // if (!record_offset.isEmpty() && record_offset < 0) … … 243 241 for (it = this->enabledFields.begin(); it != end; it++) 244 242 { 245 CField* field = *it; 246 allDomainEmpty &= !field->grid->doGridHaveDataToWrite(); 243 CField* field = *it; 247 244 std::vector<CAxis*> vecAxis = field->grid->getAxis(); 248 245 for (size_t i = 0; i < vecAxis.size(); ++i) 249 246 setAxis.insert(vecAxis[i]->getAxisOutputName()); 250 // setAxis.insert(vecAxis[i]);251 247 std::vector<CDomain*> vecDomains = field->grid->getDomains(); 252 248 for (size_t i = 0; i < vecDomains.size(); ++i) 253 249 setDomains.insert(vecDomains[i]->getDomainOutputName()); 254 // setDomains.insert(vecDomains[i]);255 250 256 251 field->resetNStep(recordOffset); … … 260 255 261 256 // create sub communicator for file 262 int color = allDomainEmpty ? 0 : 1; 263 MPI_Comm_split(server->intraComm, color, server->intraCommRank, &fileComm); 264 if (allDomainEmpty) MPI_Comm_free(&fileComm); 257 createSubComFile(); 265 258 266 259 // if (time_counter.isEmpty()) time_counter.setValue(time_counter_attr::centered); 267 260 if (time_counter_name.isEmpty()) time_counter_name = "time_counter"; 261 } 262 263 //! Initialize a file in order to write into it 264 void CFile::initRead(void) 265 { 266 if (checkRead) return; 267 createSubComFile(); 268 checkRead = true; 269 } 270 271 /*! 272 Create a sub communicator in which processes participate in reading/opening file 273 */ 274 void CFile::createSubComFile() 275 { 276 CContext* context = CContext::getCurrent(); 277 CContextServer* server = context->server; 278 279 // create sub communicator for file 280 allZoneEmpty = true; 281 std::vector<CField*>::iterator it, end = this->enabledFields.end(); 282 for (it = this->enabledFields.begin(); it != end; it++) 283 { 284 CField* field = *it; 285 bool nullGrid = (0 == field->grid); 286 allZoneEmpty &= nullGrid ? false : !field->grid->doGridHaveDataToWrite(); 287 } 288 289 int color = allZoneEmpty ? 0 : 1; 290 MPI_Comm_split(server->intraComm, color, server->intraCommRank, &fileComm); 291 if (allZoneEmpty) MPI_Comm_free(&fileComm); 268 292 } 269 293 … … 307 331 { 308 332 CTimer::get("Files : open headers").resume(); 309 if (!isOpen) openInReadMode(&(context->server->intraComm)); 333 334 if (!isOpen) openInReadMode(); 335 310 336 CTimer::get("Files : open headers").suspend(); 311 337 } 312 338 //checkSplit(); // Really need for reading? 313 339 } 340 } 341 342 /*! 343 Verify if a process participates in an opening-file communicator 344 \return true if the process doesn't participate in opening file 345 */ 346 bool CFile::isEmptyZone() 347 { 348 return allZoneEmpty; 314 349 } 315 350 … … 376 411 CContextServer* server = context->server; 377 412 378 if (!all DomainEmpty)413 if (!allZoneEmpty) 379 414 { 380 415 StdString filename = getFileOutputName(); … … 558 593 \brief Open an existing NetCDF file in read-only mode 559 594 */ 560 void CFile::openInReadMode( MPI_Comm* comm)595 void CFile::openInReadMode() 561 596 { 562 597 CContext* context = CContext::getCurrent(); 563 598 CContextServer* server = context->server; 564 MPI_Comm readComm = *comm;565 566 if (!all DomainEmpty)599 MPI_Comm readComm = this->fileComm; 600 601 if (!allZoneEmpty) 567 602 { 568 603 StdString filename = getFileOutputName(); … … 632 667 void CFile::close(void) 633 668 { 634 if (!all DomainEmpty)669 if (!allZoneEmpty) 635 670 if (isOpen) 636 671 { … … 639 674 else 640 675 this->data_in->closeFile(); 676 isOpen = false; 641 677 } 642 678 if (fileComm != MPI_COMM_NULL) MPI_Comm_free(&fileComm); … … 905 941 } 906 942 943 void CFile::setReadContextClient(CContextClient* readContextclient) 944 { 945 read_client = readContextclient; 946 } 947 948 CContextClient* CFile::getReadContextClient() 949 { 950 return read_client; 951 } 952 907 953 /*! 908 954 \brief Send a message to create a field on server side -
XIOS/dev/XIOS_DEV_CMIP6/src/node/file.hpp
r1158 r1232 89 89 void checkWriteFile(void); 90 90 void checkReadFile(void); 91 void initFile(void); 91 void initWrite(void); 92 void initRead(void); 93 bool isEmptyZone(); 92 94 93 95 /// Mutateurs /// … … 97 99 98 100 void createHeader(void); 99 void openInReadMode( MPI_Comm* readComm = NULL);101 void openInReadMode(void); 100 102 void close(void); 101 103 void readAttributesOfEnabledFieldsInReadMode(); … … 122 124 void setContextClient(CContextClient* newContextClient); 123 125 CContextClient* getContextClient(); 126 127 void setReadContextClient(CContextClient* newContextClient); 128 CContextClient* getReadContextClient(); 124 129 125 130 // Send info to server … … 162 167 CDate lastSplit; 163 168 int nbAxis, nbDomains; 164 bool isOpen; 165 bool allDomainEmpty; 169 bool isOpen; 166 170 MPI_Comm fileComm; 167 171 172 private: 173 void createSubComFile(); 174 bool checkRead; 175 bool allZoneEmpty; 176 168 177 private : 169 178 /// Propriétés privées /// 170 179 CContextClient* client; 180 CContextClient* read_client; // Context client for reading (channel between server 1 and client) 171 181 CFieldGroup* vFieldGroup; 172 182 CVariableGroup* vVariableGroup; … … 175 185 std::vector<CField*> enabledFields; 176 186 187 177 188 public: 178 189 // virtual void toBinary (StdOStream& os) const; -
XIOS/dev/XIOS_DEV_CMIP6/src/node/grid.cpp
r1215 r1232 155 155 // The record index is sometimes sent along with the data but we always 156 156 // include it in the size calculation for the sake of simplicity 157 const size_t extraSize = CEventClient::headerSize + (id.empty() ? getId() : id).size() + 2 * sizeof(size_t); 157 const size_t extraSize = CEventClient::headerSize + (id.empty() ? getId() : id).size() 158 + 2 * sizeof(size_t) 159 + sizeof(size_t); 158 160 CContext* context = CContext::getCurrent(); 159 161 int nbSrvPools = (context->hasServer) ? (context->hasClient ? context->clientPrimServer.size() : 0) : 1; … … 162 164 { 163 165 std::map<int, size_t>::const_iterator itEnd = connectedDataSize_[p].end(); 164 for (size_t k = 0; k < connectedServerRank_[p].size(); ++k) // TODO: Should change connectedServerRank_[0] to something more general166 for (size_t k = 0; k < connectedServerRank_[p].size(); ++k) 165 167 { 166 168 int rank = connectedServerRank_[p][k]; 167 std::map<int, size_t>::const_iterator it = connectedDataSize_[ 0].find(rank);169 std::map<int, size_t>::const_iterator it = connectedDataSize_[p].find(rank); 168 170 size_t count = (it != itEnd) ? it->second : 0; 169 171 … … 714 716 std::vector<boost::unordered_map<size_t,std::vector<int> > > indexServerOnElement; 715 717 CServerDistributionDescription serverDistributionDescription(getGlobalDimension(), client->serverSize); 716 serverDistributionDescription.computeServerGlobalByElement(indexServerOnElement, 717 client->clientRank, 718 client->clientSize, 719 axis_domain_order, 720 getDistributedDimension()); 718 std::vector<int> serverZeroIndex = serverDistributionDescription.computeServerGlobalByElement(indexServerOnElement, 719 client->clientRank, 720 client->clientSize, 721 axis_domain_order, 722 getDistributedDimension()); 723 724 // Even if servers have no index, they must received something from client 725 // We only use several client to send "empty" message to these servers 726 std::list<int> serverZeroIndexLeader; 727 std::list<int> serverZeroIndexNotLeader; 728 CContextClient::computeLeader(client->clientRank, client->clientSize, serverZeroIndex.size(), serverZeroIndexLeader, serverZeroIndexNotLeader); 729 for (std::list<int>::iterator it = serverZeroIndexLeader.begin(); it != serverZeroIndexLeader.end(); ++it) 730 *it = serverZeroIndex[*it]; 731 721 732 computeIndexByElement(indexServerOnElement, globalIndexOnServer_); 722 733 … … 724 735 CDistributionClient::GlobalLocalDataMap::const_iterator iteGlobalLocalIndexMap = globalLocalIndexSendToServer.end(), itGlobalLocalIndexMap; 725 736 CClientServerMapping::GlobalIndexMap::const_iterator iteGlobalMap, itbGlobalMap, itGlobalMap; 726 it GlobalMap = itbGlobalMap = globalIndexOnServer_.begin();737 itbGlobalMap = globalIndexOnServer_.begin(); 727 738 iteGlobalMap = globalIndexOnServer_.end(); 728 739 729 for ( ; itGlobalMap != iteGlobalMap; ++itGlobalMap)740 for (itGlobalMap = itbGlobalMap; itGlobalMap != iteGlobalMap; ++itGlobalMap) 730 741 { 731 742 int serverRank = itGlobalMap->first; … … 745 756 } 746 757 758 // Connected servers which really have index 747 759 for (itGlobalMap = itbGlobalMap; itGlobalMap != iteGlobalMap; ++itGlobalMap) { 748 760 connectedServerRank_[p].push_back(itGlobalMap->first); 749 761 } 750 762 763 // Connected servers which have no index at all 764 for (std::list<int>::iterator it = serverZeroIndexLeader.begin(); it != serverZeroIndexLeader.end(); ++it) 765 connectedServerRank_[p].push_back(*it); 766 767 // Even if a client has no index, it must connect to at least one server and 768 // send an "empty" data to this server 769 if (connectedServerRank_[p].empty()) 770 connectedServerRank_[p].push_back(client->clientRank % client->serverSize); 771 751 772 nbSenders[p] = clientServerMap_->computeConnectedClients(client->serverSize, client->clientSize, client->intraComm, connectedServerRank_[p]); 752 773 } -
XIOS/dev/XIOS_DEV_CMIP6/src/server_distribution_description.cpp
r887 r1232 100 100 \param [in] positionDimensionDistributed dimension of server on which we make the cut. 101 101 */ 102 voidCServerDistributionDescription::computeServerGlobalIndexInRange(const std::pair<size_t, size_t>& indexBeginEnd,102 std::vector<int> CServerDistributionDescription::computeServerGlobalIndexInRange(const std::pair<size_t, size_t>& indexBeginEnd, 103 103 int positionDimensionDistributed) 104 104 { 105 int nBand = 0; 105 106 switch (serverType_) { 106 107 case BAND_DISTRIBUTION: 107 computeBandDistribution(nServer_, positionDimensionDistributed);108 nBand = computeBandDistribution(nServer_, positionDimensionDistributed); 108 109 break; 109 110 default: … … 122 123 std::vector<int> currentIndex(dim); 123 124 124 for (int idxServer = 0; idxServer < n Server_; ++idxServer)125 for (int idxServer = 0; idxServer < nBand; ++idxServer) 125 126 { 126 127 size_t ssize = 1, idx = 0; … … 161 162 } 162 163 } 164 165 // List of servers without distribution (cause total number of server is greater than number of bands, for example) 166 std::vector<int> zeroIndexServer(nServer_-nBand); 167 for (int idxServer = nBand; idxServer < nServer_; ++idxServer) 168 zeroIndexServer[idxServer-nBand] = idxServer; 169 170 return zeroIndexServer; 163 171 } 164 172 … … 172 180 \param [in] positionDimensionDistributed dimension of server on which we make the cut. 173 181 */ 174 void CServerDistributionDescription::computeServerGlobalByElement(std::vector<boost::unordered_map<size_t,std::vector<int> > >& indexServerOnElement, 175 int clientRank, 176 int clientSize, 177 const CArray<int,1>& axisDomainOrder, 178 int positionDimensionDistributed) 179 { 182 std::vector<int> CServerDistributionDescription::computeServerGlobalByElement(std::vector<boost::unordered_map<size_t,std::vector<int> > >& indexServerOnElement, 183 int clientRank, 184 int clientSize, 185 const CArray<int,1>& axisDomainOrder, 186 int positionDimensionDistributed) 187 { 188 int nBand = 0; 180 189 switch (serverType_) { 181 190 case BAND_DISTRIBUTION: 182 computeBandDistribution(nServer_, positionDimensionDistributed);191 nBand = computeBandDistribution(nServer_, positionDimensionDistributed); 183 192 break; 184 193 default: … … 197 206 } 198 207 199 for (int idxServer = 0; idxServer < n Server_; ++idxServer)208 for (int idxServer = 0; idxServer < nBand; ++idxServer) 200 209 { 201 210 std::vector<int> elementDimension(4); … … 247 256 } 248 257 } 258 259 // List of servers without distribution (cause total number of server is greater than number of bands, for example) 260 std::vector<int> zeroIndexServer(nServer_-nBand); 261 for (int idxServer = nBand; idxServer < nServer_; ++idxServer) 262 zeroIndexServer[idxServer-nBand] = idxServer; 263 264 return zeroIndexServer; 249 265 } 250 266 … … 297 313 \param [in] nServer number of server 298 314 */ 299 voidCServerDistributionDescription::computeBandDistribution(int nServer, int positionDimensionDistributed)315 int CServerDistributionDescription::computeBandDistribution(int nServer, int positionDimensionDistributed) 300 316 { 301 317 int dim = nGlobal_.size(); … … 324 340 int positionDistributed = (1<dim) ? positionDimensionDistributed_ : 0; 325 341 nGlobTemp = nGlobal_[positionDistributed]; 326 327 for (int i = 0; i < nServer; ++i) 342 int nbBand = std::min(nGlobTemp, nServer); 343 344 for (int i = 0; i < nbBand; ++i) 328 345 { 329 346 if (0 < i) njRangeBegin[i] = njRangeEnd[i-1]; 330 njRangeSize = nGlobTemp / n Server;331 if (i < nGlobTemp%n Server) ++njRangeSize;347 njRangeSize = nGlobTemp / nbBand; 348 if (i < nGlobTemp%nbBand) ++njRangeSize; 332 349 njRangeEnd[i] = njRangeSize + njRangeBegin[i]; 333 350 } 334 njRangeEnd[nServer-1] = nGlobTemp; 351 njRangeEnd[nbBand-1] = nGlobTemp; 352 353 for (int i = nbBand; i < nServer; ++i) 354 { 355 njRangeBegin[i] = njRangeEnd[i] = 0; 356 } 335 357 336 358 for (int i = 0; i < nServer; ++i) … … 358 380 } 359 381 } 382 383 return nbBand; 360 384 } 361 385 -
XIOS/dev/XIOS_DEV_CMIP6/src/server_distribution_description.hpp
r887 r1232 38 38 39 39 void computeServerDistribution(bool doComputeGlobalIndex = false, int positionDimensionDistributed = 1); 40 voidcomputeServerGlobalIndexInRange(const std::pair<size_t, size_t>& indexBeginEnd, int positionDimensionDistributed = 1);41 voidcomputeServerGlobalByElement(std::vector<boost::unordered_map<size_t,std::vector<int> > >& indexServerOnElement,42 int rank,43 int clientSize,44 const CArray<int,1>& axisDomainOrder,45 int positionDimensionDistributed = 1);40 std::vector<int> computeServerGlobalIndexInRange(const std::pair<size_t, size_t>& indexBeginEnd, int positionDimensionDistributed = 1); 41 std::vector<int> computeServerGlobalByElement(std::vector<boost::unordered_map<size_t,std::vector<int> > >& indexServerOnElement, 42 int rank, 43 int clientSize, 44 const CArray<int,1>& axisDomainOrder, 45 int positionDimensionDistributed = 1); 46 46 47 47 std::vector<std::vector<int> > getServerIndexBegin() const; … … 52 52 53 53 protected: 54 voidcomputeBandDistribution(int nServer, int positionDimensionDistributed = 1);54 int computeBandDistribution(int nServer, int positionDimensionDistributed = 1); 55 55 void computePlanDistribution(int nServer); 56 56 void computeRangeProcIndex(int clientRank,
Note: See TracChangeset
for help on using the changeset viewer.