source: issm/branches/trunk-jpl-damage/src/c/modules/ModelProcessorx/NodesPartitioning.cpp@ 12878

Last change on this file since 12878 was 12878, checked in by cborstad, 13 years ago

merged trunk-jpl into trunk-jpl-damage through revision 12877

File size: 5.1 KB
Line 
1/*!\file: NodesPartitioning.cpp
2 * \brief: partition elements and nodes and vertices
3 */
4
5#ifdef HAVE_CONFIG_H
6 #include <config.h>
7#else
8#error "Cannot compile with HAVE_CONFIG_H symbol! run configure first!"
9#endif
10
11#include <string.h>
12#include "../../classes/objects/objects.h"
13#include "../../shared/shared.h"
14#include "../../EnumDefinitions/EnumDefinitions.h"
15#include "../../io/io.h"
16#include "../../include/include.h"
17#include "../MeshPartitionx/MeshPartitionx.h"
18#include "../ModelProcessorx/ModelProcessorx.h"
19
20void DiscontinuousGalerkinNodesPartitioning(bool** pmy_nodes,bool* my_elements, int* my_vertices, IoModel* iomodel);
21void ContinuousGalerkinNodesPartitioning(bool** pmy_nodes,bool* my_elements, int* my_vertices, IoModel* iomodel);
22
23void NodesPartitioning(bool** pmy_nodes,bool* my_elements, int* my_vertices, IoModel* iomodel, bool continuous){
24
25 /*First thing, this is a new partition for a new analysis_type, therefore, to avoid a leak, erase the nodes partition that might come through pmy_nodes: */
26 xDelete<bool>(*pmy_nodes);
27
28 /*Now, depending on whether we are running galerkin discontinous or continuous elements, carry out a different partition of the nodes: */
29 if(continuous==true)
30 ContinuousGalerkinNodesPartitioning(pmy_nodes,my_elements, my_vertices, iomodel);
31 else
32 DiscontinuousGalerkinNodesPartitioning(pmy_nodes,my_elements, my_vertices, iomodel);
33}
34
35void ContinuousGalerkinNodesPartitioning(bool** pmy_nodes,bool* my_elements, int* my_vertices, IoModel* iomodel){
36
37 /*as many nodes as there are vertices */
38 int numberofvertices;
39
40 /*output: */
41 bool* my_nodes=NULL;
42
43 /*Fetch parameters: */
44 iomodel->Constant(&numberofvertices,MeshNumberofverticesEnum);
45
46 my_nodes=xNew<bool>(numberofvertices);
47 for(int i=0;i<numberofvertices;i++) my_nodes[i]=(bool)my_vertices[i];
48
49 /*Assign output pointers:*/
50 *pmy_nodes=my_nodes;
51}
52
53
54void DiscontinuousGalerkinNodesPartitioning(bool** pmy_nodes,bool* my_elements, int* my_vertices, IoModel* iomodel){
55
56 int numberofelements;
57
58 /*Fetch parameters: */
59 iomodel->Constant(&numberofelements,MeshNumberofelementsEnum);
60
61 /*each element has it own nodes (as many as vertices) + additional nodes from neighbouring elements for each edge. This yields to a very different partition for
62 * the nodes and the vertices. The vertices are similar to continuous galerkin, but the nodes partitioning involves edges, which mess up sorting of
63 * ids. */
64
65 int i,j;
66 int dim;
67
68 /*output: */
69 bool* my_nodes=NULL;
70
71 int i1,i2;
72 int cols;
73 int e1,e2;
74 int pos;
75 int numberofedges;
76 int *edges = NULL;
77 int *elements = NULL;
78
79 /*Fetch parameters: */
80 iomodel->Constant(&dim,MeshDimensionEnum);
81
82 /*Build discontinuous node partitioning
83 * - there are three nodes per element (discontinous)
84 * - for each element present of each partition, its three nodes will be in this partition
85 * - the edges require the dofs of the 2 nodes of each elements sharing the edge.
86 * if the 2 elements sharing the edge are on 2 different cpus, we must duplicate
87 * the two nodes that are not on the cpus so that the edge can access the dofs of
88 * all its 4 nodes
89 */
90
91 /*Allocate*/
92 my_nodes=xNewZeroInit<bool>(3*numberofelements);
93
94 /*First: add all the nodes of all the elements belonging to this cpu*/
95 if (dim==2){
96 for (i=0;i<numberofelements;i++){
97 if (my_elements[i]){
98 my_nodes[3*i+0]=true;
99 my_nodes[3*i+1]=true;
100 my_nodes[3*i+2]=true;
101 }
102 }
103 }
104 else{
105 _error2_("not implemented yet");
106 }
107
108 /*Second: add all missing nodes*/
109
110 /*Get edges and elements*/
111 iomodel->FetchData(&edges,&numberofedges,&cols,MeshEdgesEnum);
112 iomodel->FetchData(&elements,NULL,NULL,MeshElementsEnum);
113 if (cols!=4) _error2_("field edges should have 4 columns");
114
115 /*!All elements have been partitioned above, only create elements for this CPU: */
116 for (i=0;i<numberofedges;i++){
117
118 /*Get left and right elements*/
119 e1=edges[4*i+2]-1; //edges are [node1 node2 elem1 elem2]
120 e2=edges[4*i+3]-1; //edges are [node1 node2 elem1 elem2]
121
122 /* 1) If the element e1 is in the current partition
123 * 2) and if the edge of the element is shared by another element (internal edge)
124 * 3) and if this element is not in the same partition:
125 * we must clone the nodes on this partition so that the loads (Numericalflux)
126 * will have access to their properties (dofs,...)*/
127 if(my_elements[e1] && e2!=-2 && !my_elements[e2]){
128
129 /*1: Get vertices ids*/
130 i1=edges[4*i+0];
131 i2=edges[4*i+1];
132
133 /*2: Get the column where these ids are located in the index*/
134 pos=UNDEF;
135 for(j=0;j<3;j++){
136 if (elements[3*e2+j]==i1) pos=j;
137 }
138
139 /*3: We have the id of the elements and the position of the vertices in the index
140 * we can now create the corresponding nodes:*/
141 if (pos==0){
142 my_nodes[e2*3+0]=true;
143 my_nodes[e2*3+2]=true;
144 }
145 else if(pos==1){
146 my_nodes[e2*3+1]=true;
147 my_nodes[e2*3+0]=true;
148 }
149 else if (pos==2){
150 my_nodes[e2*3+2]=true;
151 my_nodes[e2*3+1]=true;
152 }
153 else{
154 _error2_("Problem in edges creation");
155 }
156 }
157 }
158
159 /*Free data: */
160 xDelete<int>(elements);
161 xDelete<int>(edges);
162
163 /*Assign output pointers:*/
164 *pmy_nodes=my_nodes;
165}
Note: See TracBrowser for help on using the repository browser.