Sierra Toolkit  Version of the Day
UnitTestCrackMesh.cpp
1 /*------------------------------------------------------------------------*/
2 /* Copyright 2010 Sandia Corporation. */
3 /* Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive */
4 /* license for use of this work by or on behalf of the U.S. Government. */
5 /* Export of this program may require a license from the */
6 /* United States Government. */
7 /*------------------------------------------------------------------------*/
8 
9 #include <stdexcept>
10 
11 #include <stk_util/unit_test_support/stk_utest_macros.hpp>
12 
13 #include <stk_mesh/fixtures/QuadFixture.hpp>
14 #include <stk_mesh/fixtures/HexFixture.hpp>
15 
16 //----------------------------------------------------------------------------
17 
18 STKUNIT_UNIT_TEST ( UnitTestCrackMesh , VerifyDestroy2D )
19 {
20  // In 2D, build a fresh 3x3 mesh each loop iteration, destroying a different
21  // single element each time.
22 
23  stk_classic::ParallelMachine pm = MPI_COMM_WORLD ;
24  const unsigned p_rank = stk_classic::parallel_machine_rank( pm );
25 
26  const unsigned nx = 3 , ny = 3 ;
27 
28  for ( unsigned iy = 0 ; iy < ny ; ++iy ) {
29  for ( unsigned ix = 0 ; ix < nx ; ++ix ) {
30  stk_classic::mesh::fixtures::QuadFixture fixture( pm , nx , ny );
31  fixture.m_fem_meta.commit();
32  fixture.generate_mesh();
33 
34  fixture.m_bulk_data.modification_begin();
35 
36  stk_classic::mesh::Entity * elem = fixture.elem( ix , iy );
37 
38  if ( elem && p_rank == elem->owner_rank() ) {
39  stk_classic::mesh::Entity * tmp = elem ;
40  fixture.m_bulk_data.destroy_entity( tmp );
41  }
42 
43  fixture.m_bulk_data.modification_end();
44 
45  if ( elem ) {
46  STKUNIT_EXPECT_TRUE ( elem->log_query() == stk_classic::mesh::EntityLogDeleted );
47  }
48  }
49  }
50 }
51 
52 STKUNIT_UNIT_TEST ( UnitTestCrackMesh , VerifyDestroy3D )
53 {
54  // In 3D, build a 3x3x3 mesh each loop iteration, destroying a different
55  // single element each time.
56 
57  stk_classic::ParallelMachine pm = MPI_COMM_WORLD ;
58  const unsigned p_rank = stk_classic::parallel_machine_rank( pm );
59 
60  const unsigned nx = 3 , ny = 3 , nz = 3 ;
61 
62  for ( unsigned iz = 0 ; iz < nz ; ++iz ) {
63  for ( unsigned iy = 0 ; iy < ny ; ++iy ) {
64  for ( unsigned ix = 0 ; ix < nx ; ++ix ) {
65  stk_classic::mesh::fixtures::HexFixture fixture( pm , nx , ny , nz );
66  fixture.m_fem_meta.commit();
67  fixture.generate_mesh();
68 
69  fixture.m_bulk_data.modification_begin();
70 
71  stk_classic::mesh::Entity * elem = fixture.elem( ix , iy , iz );
72 
73  if ( elem && p_rank == elem->owner_rank() ) {
74  stk_classic::mesh::Entity * tmp = elem ;
75  fixture.m_bulk_data.destroy_entity( tmp );
76  }
77 
78  fixture.m_bulk_data.modification_end();
79 
80  if ( elem ) {
81  STKUNIT_EXPECT_TRUE ( elem->log_query() == stk_classic::mesh::EntityLogDeleted );
82  }
83  }
84  }
85  }
86 }
87 
88 //----------------------------------------------------------------------------
89 
90 STKUNIT_UNIT_TEST ( UnitTestCrackMesh , verifyBoxGhosting )
91 {
92  // Start with a normal hex fixture, then crack it, and check to see
93  // if all (incl ghosted) copies get updated.
94 
95  // Make the hex fixture
96 
97  stk_classic::mesh::fixtures::HexFixture fixture( MPI_COMM_WORLD, 2,2,2 );
98  fixture.m_fem_meta.commit();
99  fixture.generate_mesh();
100 
101  stk_classic::mesh::BulkData & mesh = fixture.m_bulk_data;
102 
103  // Hardwire which entities are being modified. Note that not every
104  // process will know about these entities
105 
106  stk_classic::mesh::Entity * const old_node = fixture.node(0,1,1);
107 
108  stk_classic::mesh::Entity * const right_element = fixture.elem(0,0,1);
109 
110  unsigned right_ordinal = 0;
111  unsigned new_node_id = 28;
112 
113  // If this process knows about both entities, compute the ordinal
114  // of the relation from right_element to old_node
115 
116  if ( old_node && right_element ) {
118 
119  for (; rel.first != rel.second; ++rel) {
120  if ( (rel.first->entity()) == right_element) {
121  right_ordinal = rel.first->identifier();
122  }
123  }
124  }
125 
126  // Crack the mesh
127 
128  mesh.modification_begin();
129 
130  //only crack the mesh if I own the element
131  if ( right_element &&
132  right_element->owner_rank() == mesh.parallel_rank() ) {
133 
134  const stk_classic::mesh::PartVector no_parts;
135 
136  // create a new node
137  stk_classic::mesh::Entity & new_node = mesh.declare_entity(stk_classic::mesh::fem::FEMMetaData::NODE_RANK, new_node_id, no_parts);
138 
139  // destroy right_element's relation to old_node, replace with a
140  // relation to new node
141  mesh.destroy_relation(*right_element, *old_node, right_ordinal);
142  mesh.declare_relation(*right_element, new_node, right_ordinal);
143  }
144 
145  mesh.modification_end();
146 
147  // Now that modification_end has been called, all processes that know
148  // about right_element should know about the crack.
149 
150  if ( right_element ) {
151  stk_classic::mesh::PairIterRelation rel = right_element->relations();
152  stk_classic::mesh::Entity & new_node = * (rel.first[right_ordinal].entity());
153 
154  STKUNIT_EXPECT_TRUE ( new_node.identifier() == new_node_id );
155  }
156 }
157 
158 //----------------------------------------------------------------------------
void declare_relation(Entity &e_from, Entity &e_to, const RelationIdentifier local_id)
Declare a relation and its converse between entities in the same mesh.
bool destroy_relation(Entity &e_from, Entity &e_to, const RelationIdentifier local_id)
Remove all relations between two entities.
EntityModificationLog log_query() const
Query the current state of the entity log.
Definition: Entity.hpp:125
unsigned parallel_machine_rank(ParallelMachine parallel_machine)
Member function parallel_machine_rank ...
Definition: Parallel.cpp:29
bool modification_end()
Parallel synchronization of modifications and transition to the guaranteed parallel consistent state...
bool modification_begin()
Begin a modification phase during which the mesh bulk data could become parallel inconsistent. This is a parallel synchronous call. The first time this method is called the mesh meta data is verified to be committed and parallel consistent. An exception is thrown if this verification fails.
Definition: BulkData.cpp:172
PairIterRelation relations() const
All Entity relations for which this entity is a member. The relations are ordered from lowest entity-...
Definition: Entity.hpp:161
Manager for an integrated collection of entities, entity relations, and buckets of field data...
Definition: BulkData.hpp:49
A fundamental unit within the discretization of a problem domain, including but not limited to nodes...
Definition: Entity.hpp:120
MPI_Comm ParallelMachine
Definition: Parallel.hpp:32
unsigned parallel_rank() const
Rank of the parallel machine&#39;s local processor.
Definition: BulkData.hpp:85
Entity & declare_entity(EntityRank ent_rank, EntityId ent_id, const PartVector &parts)
Create or retrieve a locally owned entity of a given rank and id.
Definition: BulkData.cpp:215
EntityId identifier() const
Identifier for this entity which is globally unique for a given entity type.
Definition: Entity.hpp:133
std::vector< Part *> PartVector
Collections of parts are frequently maintained as a vector of Part pointers.
Definition: Types.hpp:31
unsigned owner_rank() const
Parallel processor rank of the processor which owns this entity.
Definition: Entity.hpp:175