1 /*=========================================================================
2
3 Program: Visualization Toolkit
4 Module: vtkPConvertToMultiBlockDataSet.cxx
5
6 Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7 All rights reserved.
8 See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9
10 This software is distributed WITHOUT ANY WARRANTY; without even
11 the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12 PURPOSE. See the above copyright notice for more information.
13
14 =========================================================================*/
15 #include "vtkPConvertToMultiBlockDataSet.h"
16
17 #include "vtkCommunicator.h"
18 #include "vtkMultiBlockDataSet.h"
19 #include "vtkMultiProcessController.h"
20 #include "vtkObjectFactory.h"
21 #include "vtkPartitionedDataSet.h"
22 #include "vtkPartitionedDataSetCollection.h"
23 #include "vtkSmartPointer.h"
24
25 vtkObjectFactoryNewMacro(vtkPConvertToMultiBlockDataSet);
vtkCxxSetObjectMacro(vtkPConvertToMultiBlockDataSet,Controller,vtkMultiProcessController)26 vtkCxxSetObjectMacro(vtkPConvertToMultiBlockDataSet, Controller, vtkMultiProcessController)
27 //----------------------------------------------------------------------------
28 vtkPConvertToMultiBlockDataSet::vtkPConvertToMultiBlockDataSet()
29 : Controller(nullptr)
30 {
31 this->SetController(vtkMultiProcessController::GetGlobalController());
32 }
33
34 //----------------------------------------------------------------------------
~vtkPConvertToMultiBlockDataSet()35 vtkPConvertToMultiBlockDataSet::~vtkPConvertToMultiBlockDataSet()
36 {
37 this->SetController(nullptr);
38 }
39
40 //----------------------------------------------------------------------------
RequestData(vtkInformation * request,vtkInformationVector ** inputVector,vtkInformationVector * outputVector)41 int vtkPConvertToMultiBlockDataSet::RequestData(
42 vtkInformation* request, vtkInformationVector** inputVector, vtkInformationVector* outputVector)
43 {
44 vtkSmartPointer<vtkPartitionedDataSetCollection> input;
45 if (auto pdc = vtkPartitionedDataSetCollection::GetData(inputVector[0], 0))
46 {
47 input = pdc;
48 }
49 else if (auto pd = vtkPartitionedDataSet::GetData(inputVector[0], 0))
50 {
51 input = vtkSmartPointer<vtkPartitionedDataSetCollection>::New();
52 input->SetPartitionedDataSet(0, pd);
53 }
54
55 const int numRanks = this->Controller ? this->Controller->GetNumberOfProcesses() : 1;
56 if (numRanks == 1 || input == nullptr || input->GetNumberOfPartitionedDataSets() == 0)
57 {
58 // nothing to do.
59 return this->Superclass::RequestData(request, inputVector, outputVector);
60 }
61
62 auto output = vtkMultiBlockDataSet::GetData(outputVector, 0);
63
64 // ensure that we have exactly the same number of partitions on all ranks.
65 vtkNew<vtkPartitionedDataSetCollection> clone;
66 clone->ShallowCopy(input);
67
68 const auto count = input->GetNumberOfPartitionedDataSets();
69 std::vector<unsigned int> piece_counts(count);
70 for (unsigned int cc = 0; cc < count; ++cc)
71 {
72 piece_counts[cc] = clone->GetPartitionedDataSet(cc)
73 ? clone->GetPartitionedDataSet(cc)->GetNumberOfPartitions()
74 : 0;
75 }
76
77 std::vector<unsigned int> result(piece_counts.size());
78 this->Controller->AllReduce(
79 &piece_counts[0], &result[0], static_cast<vtkIdType>(count), vtkCommunicator::MAX_OP);
80
81 for (unsigned int cc = 0; cc < count; ++cc)
82 {
83 if (result[cc] > 0)
84 {
85 if (clone->GetPartitionedDataSet(cc) == nullptr)
86 {
87 clone->SetPartitionedDataSet(cc, vtkNew<vtkPartitionedDataSet>{});
88 }
89 clone->GetPartitionedDataSet(cc)->SetNumberOfPartitions(result[cc]);
90 }
91 }
92 return this->Execute(clone, output) ? 1 : 0;
93 }
94
95 //----------------------------------------------------------------------------
PrintSelf(ostream & os,vtkIndent indent)96 void vtkPConvertToMultiBlockDataSet::PrintSelf(ostream& os, vtkIndent indent)
97 {
98 this->Superclass::PrintSelf(os, indent);
99 }
100