MOAB: Mesh Oriented datABase
(version 5.4.1)
|
00001 /* 00002 * imoab_ptest_C.cpp 00003 * 00004 * push parallel mesh into moab, using iMoab API, C version 00005 * This program shows how to push a mesh into MOAB in parallel using iMoab, with sufficient 00006 * information to resolve boundary sharing and exchange a layer of ghost information. 00007 * 00008 * After resolving the sharing, mesh is saved to a file, then read back again, in parallel 00009 * the mesh is a quad mesh, 2x2 on each task, 00010 * by default, this test is run on 2 processors 00011 00012 * Test is similar to itaps/iMeshP_unit_tests.cpp, and with imoab_ptest.F, fortran 77 version 00013 * 00014 * 00015 * Create a mesh: 00016 * Groups of four quads will be arranged into parts as follows: 00017 * +------+------+------+------+------+----- 00018 * | | | 00019 * | | | 00020 * + Part 0 + Part 2 + Part 4 00021 * | | | 00022 * | | | 00023 * +------+------+------+------+------+----- 00024 * | | | 00025 * | | | 00026 * + Part 1 + Part 3 + Part 5 00027 * | | | 00028 * | | | 00029 * +------+------+------+------+------+----- 00030 * 00031 * Vertices will be enumerated as follows: 00032 * 1------6-----11-----16-----21-----26----- > x x from 0, 1, 2 00033 * | | | 00034 * | | | 00035 * 2 7 12 17 22 27 00036 * | | | 00037 * | | | 00038 * 3------8-----13-----18-----23-----28----- 00039 * | | | 00040 * | | | 00041 * 4 9 14 19 24 29 00042 * | | | 00043 * | | | 00044 * 5-----10-----15-----20-----25-----30----- 00045 * | 00046 * y varies from 0 to 4 00047 * 00048 * Processor 0 will have vertices 1, 2, 3, 6, 7, 8, 11, 12, 13 00049 * and 4 quads, with ids from 1 to 4, and connectivity 00050 * 1, 2, 7, 6; 2, 3, 8, 7; 6 ,7, 12, 11; 7, 8, 13, 12 00051 * Processor 1 will have vertices 3, 4, 5, 8, 9, 10, 13, 14, 15 00052 * and 4 quads, with ids from 5 to 8, and connectivity 00053 * 3, 4, 8, 9; 4, 5, 10, 9; 8, 9, 14, 13; 9, 10, 15, 14, 00054 * and so on 00055 * 00056 * Vertex Global IDs will be used to resolve sharing 00057 * 00058 * Element IDs will be [4*rank+1,4*rank+5] 00059 * */ 00060 00061 /* 00062 * #define ERROR(rval) if (0 .ne. rval) call exit(1) 00063 */ 00064 00065 #include "moab/MOABConfig.h" 00066 #include "moab_mpi.h" 00067 #include "moab/iMOAB.h" 00068 #include <cstdio> 00069 #include <cstring> 00070 #include <vector> 00071 00072 #define ERROR( rc, msg ) \ 00073 if( 0 != ( rc ) ) \ 00074 { \ 00075 printf( "error %s", msg ); \ 00076 return 1; \ 00077 } 00078 00079 int main( int argc, char** argv ) 00080 { 00081 int my_id, num_procs, ix, iy, numv, nume; 00082 int dime, lco, mbtype, blockid, npe; 00083 char appname[10] = "IMTEST"; 00084 /* coordinates for 9 vertices */ 00085 double coordinates[27], deltax, deltay; 00086 int ids[9] = { 1, 2, 3, 6, 7, 8, 11, 12, 13 }; 00087 int connec[16] = { 1, 2, 5, 4, 2, 3, 6, 5, 4, 5, 8, 7, 5, 6, 9, 8 }; 00088 /* used for ghosting */ 00089 int dimgh, bridge, num_layers; 00090 double coords_core[27] = { 0., 0., 0., 0., 1., 0., 0., 2., 0., 1., 0., 0., 1., 1., 00091 0., 1., 2., 0., 2., 0., 0., 2., 1., 0., 2., 2., 0. }; 00092 int appID, compid; 00093 iMOAB_AppID pid = &appID; 00094 00095 MPI_Init( &argc, &argv ); 00096 MPI_Comm comm = MPI_COMM_WORLD; 00097 00098 MPI_Comm_size( comm, &num_procs ); 00099 MPI_Comm_rank( comm, &my_id ); 00100 00101 ErrCode rc = iMOAB_Initialize( argc, argv ); 00102 ERROR( rc, "can't initialize" ); 00103 if( !my_id ) printf( " I'm process %d out of %d\n", my_id, num_procs ); 00104 00105 appname[7] = 0; // make sure it is NULL 00106 compid = 8; // given number, external application number 00107 rc = iMOAB_RegisterApplication( appname, &comm, &compid, pid ); 00108 ERROR( rc, " can't register app" ); 00109 /* create first 9 vertices, in a square 3x3; */ 00110 deltax = ( my_id / 2 ) * 2.; 00111 deltay = ( my_id % 2 ) * 2.; 00112 ix = ( my_id / 2 ) * 10; 00113 iy = my_id % 2 * 2; 00114 for( int i = 0; i < 9; i++ ) 00115 { 00116 coordinates[3 * i] = coords_core[3 * i] + deltax; 00117 coordinates[3 * i + 1] = coords_core[3 * i + 1] + deltay; 00118 coordinates[3 * i + 2] = coords_core[3 * i + 2]; 00119 00120 /* translate the ids too, by multiples of 10 or add 2, depending on my_id*/ 00121 ids[i] = ids[i] + ix + iy; 00122 } 00123 numv = 9; 00124 nume = 4; 00125 lco = numv * 3; 00126 dime = 3; 00127 rc = iMOAB_CreateVertices( pid, &lco, &dime, coordinates ); 00128 ERROR( rc, "can't create vertices" ); 00129 /* create now 4 quads with those 9 vertices*/ 00130 mbtype = 3; 00131 blockid = 100; 00132 npe = 4; 00133 rc = iMOAB_CreateElements( pid, &nume, &mbtype, &npe, connec, &blockid ); 00134 ERROR( rc, "can't create elements" ); 00135 00136 rc = iMOAB_ResolveSharedEntities( pid, &numv, ids ); 00137 ERROR( rc, "can't resolve shared ents" ); 00138 00139 // test iMOAB_ReduceTagsMax on a tag 00140 int tagType = DENSE_DOUBLE; 00141 int num_components = 1; 00142 int tagIndex = 0; // output 00143 00144 rc = iMOAB_DefineTagStorage( pid, "afrac:ifrac", &tagType, &num_components, &tagIndex ); 00145 ERROR( rc, "failed to create tags afrac:ifrac " ); 00146 double af[4] = {1.,1.,1.,1.}; 00147 int entType = 1; // cells 00148 rc = iMOAB_SetDoubleTagStorage( pid, "afrac", &nume, &entType, af); 00149 ERROR( rc, "failed to set tag afrac " ); 00150 /* write out the mesh file to disk, in parallel, if h5m*/ 00151 #ifdef MOAB_HAVE_HDF5_PARALLEL 00152 char wopts[100] = "PARALLEL=WRITE_PART"; 00153 char outfile[32] = "whole.h5m"; 00154 rc = iMOAB_WriteMesh( pid, outfile, wopts ); 00155 ERROR( rc, "can't write mesh" ); 00156 #endif 00157 00158 // define repeat tags 00159 rc = iMOAB_DefineTagStorage( pid, "ofrac:afrac:ofrad", &tagType, &num_components, &tagIndex ); 00160 ERROR( rc, "failed to create tags ofrac:afrac:ofrad " ); 00161 00162 // write again 00163 #ifdef MOAB_HAVE_HDF5_PARALLEL 00164 rc = iMOAB_WriteMesh( pid, outfile, wopts ); 00165 ERROR( rc, "can't write mesh 3\n" ); 00166 #endif 00167 00168 tagType = DENSE_INTEGER; 00169 rc = iMOAB_DefineTagStorage( pid, "INTFIELD", &tagType, &num_components, &tagIndex ); 00170 ERROR( rc, "failed to get tag INTFIELD " ); 00171 // set some values 00172 std::vector< int > valstest( numv ); 00173 for( int k = 0; k < numv; k++ ) 00174 { 00175 valstest[k] = my_id + k; 00176 } 00177 int num_tag_storage_length = numv * num_components; 00178 entType = 0; // vertex 00179 // create an integer tag 00180 00181 rc = iMOAB_SetIntTagStorage( pid, "INTFIELD", &num_tag_storage_length, &entType, &valstest[0] ); 00182 ERROR( rc, "failed to set tag INTFIELD " ); 00183 00184 rc = iMOAB_ReduceTagsMax( pid, &tagIndex, &entType ); 00185 ERROR( rc, "failed reduce tags max " ); 00186 00187 /* see ghost elements */ 00188 dimgh = 2; /* will ghost quads, topological dim 2 */ 00189 bridge = 0; /* use vertex as bridge */ 00190 num_layers = 1; /* so far, one layer only */ 00191 rc = iMOAB_DetermineGhostEntities( pid, &dimgh, &num_layers, &bridge ); 00192 ERROR( rc, "can't determine ghosts" ); 00193 00194 00195 /* write out the mesh file to disk, in parallel, if h5m*/ 00196 #ifdef MOAB_HAVE_HDF5_PARALLEL 00197 rc = iMOAB_WriteMesh( pid, outfile, wopts ); 00198 ERROR( rc, "can't write mesh" ); 00199 #endif 00200 /* all done. de-register and finalize */ 00201 rc = iMOAB_DeregisterApplication( pid ); 00202 ERROR( rc, "can't de-register app" ); 00203 00204 rc = iMOAB_Finalize(); 00205 ERROR( rc, "can't finalize" ); 00206 00207 MPI_Finalize(); 00208 return 0; 00209 }