Actual source code: unstructured_2d.c
1: #ifdef PETSC_RCS_HEADER
2: static char vcid[] = "$Id: unstructured_2d.c,v 1.5 2000/02/01 17:02:51 knepley Exp $";
3: #endif
5: static char help[] = "This example deals with 2D unstructured meshes.\n\n";
7: #include "unstructured_2d.h"
9: /*
10: Here we will create a series of refined 2D unstructured meshes.
11: */
12: #undef __FUNCT__
14: int main(int argc, char **args)
15: {
16: MeshContext ctx; /* Holds problem specific information */
17: int ierr;
20: PetscInitialize(&argc, &args, 0, help); CHKERRABORT(PETSC_COMM_WORLD, ierr);
22: MeshContextCreate(PETSC_COMM_WORLD, &ctx); CHKERRABORT(PETSC_COMM_WORLD, ierr);
23: MeshContextRun(ctx); CHKERRABORT(PETSC_COMM_WORLD, ierr);
24: MeshContextDestroy(ctx); CHKERRABORT(PETSC_COMM_WORLD, ierr);
26: CHKMEMQ;
27: PetscFinalize();
28: return(0);
29: }
31: /*--------------------------------------------- MeshContext Creation -------------------------------------------------*/
32: #undef __FUNCT__
34: /*@
35: MeshContextCreate - This function initializes the Mesh context.
37: Collective on MPI_Comm
39: Input Parameter:
40: . comm - The communicator
42: Output Parameter:
43: . mCtx - The MeshContext
45: Level: beginner
47: .keywords: Mesh, context, create
48: .seealso: MeshContextDestroy(), MeshContextPrint(), MeshContextSetup()
49: @*/
50: int MeshContextCreate(MPI_Comm comm, MeshContext *mCtx)
51: {
52: MeshContext ctx;
55: /* Setup context */
56: PetscHeaderCreate(ctx, _MeshContext, int, PETSC_VIEWER_COOKIE, -1, "context", comm, 0, 0);
57: PetscLogObjectCreate(ctx);
58: PetscLogObjectMemory(ctx, sizeof(struct _MeshContext));
60: /* Initialize subobjects */
61: ctx->mesh = PETSC_NULL;
62: /* Set for vertices only */
63: ctx->numLocalNodes = 3;
64: /* Setup domain */
65: ctx->geometryCtx.size[0] = 2.0;
66: ctx->geometryCtx.size[1] = 2.0;
67: ctx->geometryCtx.start[0] = 0.0;
68: ctx->geometryCtx.start[1] = 0.0;
69: /* Setup refinement */
70: ctx->geometryCtx.maxArea = 0.5;
71: ctx->geometryCtx.areaFunc = PointFunctionConstant;
72: ctx->geometryCtx.areaCtx = PETSC_NULL;
73: /* Initialize problem loop */
74: ctx->numRefine = 0;
75: ctx->numCoarsen = 0;
77: *mCtx = ctx;
78: return(0);
79: }
81: #undef __FUNCT__
83: /*@
84: MeshContextDestroy - This function destroys the Mesh context.
86: Collective on MeshContext
88: Input Parameter:
89: . ctx - The MeshContext
91: Level: beginner
93: .keywords: Mesh, context, destroy
94: .seealso: MeshContextCreate()
95: @*/
96: int MeshContextDestroy(MeshContext ctx)
97: {
99: if (--ctx->refct > 0) SETERRQ(PETSC_ERR_PLIB, "Mesh context should not be referenced more than once");
100: PetscLogObjectDestroy(ctx);
101: PetscHeaderDestroy(ctx);
102: return(0);
103: }
105: /*------------------------------------------------ Mesh Creation -----------------------------------------------------*/
106: /*@
107: MeshContextSetup - This function initializes all internal variables through options and creates the mesh.
109: Collective on MeshContext
111: Input Parameter:
112: . ctx - A MeshContext
114: Options Database Keys:
115: + num_local_nodes - The number of nodes on an element
116: . num_refine - The number of times to refine the mesh
117: . num_coarsen - The number of times to coarsen the mesh
118: - mesh_max_area - The maximum area of an element after refinement
120: Level: beginner
122: .seealso MeshContextCleanup(), MeshContextCreate()
123: @*/
124: #undef __FUNCT__
126: int MeshContextSetup(MeshContext ctx)
127: {
128: PetscTruth opt;
129: int ierr;
132: /* The number of local nodes (usually either 3 or 6) */
133: PetscOptionsGetInt(PETSC_NULL, "-num_local_nodes", &ctx->numLocalNodes, &opt);
134: /* The number of times to refine the mesh */
135: PetscOptionsGetInt(PETSC_NULL, "-num_refine", &ctx->numRefine, &opt);
136: /* The number of times to coarsen the mesh */
137: PetscOptionsGetInt(PETSC_NULL, "-num_coarsen", &ctx->numCoarsen, &opt);
138: /* Setup refinement */
139: PetscOptionsGetReal("mesh", "-max_area", &ctx->geometryCtx.maxArea, &opt);
141: MeshContextCreateMesh(ctx);
142: return(0);
143: }
145: #undef __FUNCT__
147: /*@
148: MeshContextCreateMesh - This function creates a mesh
150: Collective on MeshContext
152: Input Parameter:
153: . ctx - A MeshContext
155: Level: beginner
157: .seealso MeshContextRefineMesh(), MeshContextSetup(), MeshContextCleanup()
158: @*/
159: int MeshContextCreateMesh(MeshContext ctx)
160: {
161: MeshGeometryContext *geomCtx = &ctx->geometryCtx;
162: int meshInfo[4], globalMeshInfo[4];
163: char name[256];
164: int ierr;
167: /* Setup mesh boundary */
168: MeshBoundary2DCreateSimple(ctx->comm, &ctx->geometryCtx, &ctx->boundaryCtx);
169: /* Construct the mesh */
170: MeshCreate(ctx->comm, &ctx->mesh);
171: MeshSetDimension(ctx->mesh, 2);
172: MeshSetPeriodicDimension(ctx->mesh, 0, geomCtx->isPeriodic[0]);
173: MeshSetPeriodicDimension(ctx->mesh, 1, geomCtx->isPeriodic[1]);
174: MeshSetNumCorners(ctx->mesh, 6);
175: MeshSetBoundary(ctx->mesh, &ctx->boundaryCtx);
176: sprintf(name, "mesh.r%.4g", geomCtx->maxArea);
177: PetscObjectSetName((PetscObject) ctx->mesh, name);
178: MeshSetFromOptions(ctx->mesh);
179: if (ctx->geometryCtx.areaCtx != PETSC_NULL) {
180: MeshSetUserContext(ctx->mesh, ctx->geometryCtx.areaCtx);
181: } else {
182: MeshSetUserContext(ctx->mesh, &ctx->geometryCtx.maxArea);
183: }
184: MeshBoundary2DDestroy(ctx->comm, &ctx->boundaryCtx);
185: /* Output mesh information */
186: MeshGetInfo(ctx->mesh, &meshInfo[0], &meshInfo[1], &meshInfo[2], &meshInfo[3]);
187: MPI_Allreduce(meshInfo, globalMeshInfo, 4, MPI_INT, MPI_SUM, ctx->comm);
188: PetscPrintf(ctx->comm, "Elements: %d Vertices: %d Nodes: %d Edges: %d\n",
189: globalMeshInfo[3], meshInfo[0], globalMeshInfo[1], globalMeshInfo[2]);
191: return(0);
192: }
194: #undef __FUNCT__
196: /*@
197: MeshContextRefineMesh - This function refines the mesh
199: Collective on MeshContext
201: Input Parameters:
202: . ctx - A MeshContextContext
204: Level: beginner
206: .seealso MeshContextCoarsenMesh(), MeshContextCreateMesh(), MeshContextCleanup()
207: @*/
208: int MeshContextRefineMesh(MeshContext ctx)
209: {
210: MeshGeometryContext *geomCtx = &ctx->geometryCtx;
211: Mesh refMesh;
212: int meshInfo[4], globalMeshInfo[4];
213: char name[256];
214: int ierr;
217: /* Decrease feature size */
218: geomCtx->maxArea *= 0.5;
219: /* Construct a refined mesh */
220: MeshRefine(ctx->mesh, geomCtx->areaFunc, &refMesh);
221: if (geomCtx->areaCtx != PETSC_NULL) {
222: MeshSetUserContext(refMesh, geomCtx->areaCtx);
223: } else {
224: MeshSetUserContext(refMesh, &geomCtx->maxArea);
225: }
226: MeshSetOptionsPrefix(refMesh, "ref_");
227: sprintf(name, "mesh.r%.4g", geomCtx->maxArea);
228: PetscObjectSetName((PetscObject) refMesh, name);
229: MeshSetFromOptions(refMesh);
230: #ifdef PETSC_USE_BOPT_g
231: CHKMEMQ;
232: #endif
233: /* Output new mesh information */
234: MeshGetInfo(refMesh, &meshInfo[0], &meshInfo[1], &meshInfo[2], &meshInfo[3]);
235: MPI_Allreduce(meshInfo, globalMeshInfo, 4, MPI_INT, MPI_SUM, ctx->comm);
236: PetscPrintf(ctx->comm, "Elements: %d Vertices: %d Nodes: %d Edges: %d\n",
237: globalMeshInfo[3], meshInfo[0], globalMeshInfo[1], globalMeshInfo[2]);
239: /* Replace old mesh with refined mesh */
240: MeshDestroy(ctx->mesh);
241: ctx->mesh = refMesh;
242: return(0);
243: }
245: #undef __FUNCT__
247: /*@
248: MeshContextCoarsenMesh - This function coarsen the mesh
250: Collective on MeshContext
252: Input Parameters:
253: . ctx - A MeshContextContext
255: Level: beginner
257: .seealso MeshContextRefineMesh(), MeshContextCreateMesh(), MeshContextCleanup()
258: @*/
259: int MeshContextCoarsenMesh(MeshContext ctx)
260: {
262: SETERRQ(PETSC_ERR_SUP, "No coarsening available yet");
263: return(0);
264: }
266: #undef __FUNCT__
268: /*@
269: MeshContextSetup - This function destroys all internal variables including the mesh.
271: Collective on MeshContext
273: Input Parameter:
274: . ctx - A MeshContext
276: Level: beginner
278: .seealso MeshContextSetup(), MeshContextCreate()
279: @*/
280: int MeshContextCleanup(MeshContext ctx)
281: {
285: MeshDestroy(ctx->mesh);
286: return(0);
287: }
289: /*---------------------------------------------- Sanity Checks ------------------------------------------------------*/
291: /*---------------------------------------------- Problem Callbacks --------------------------------------------------*/
293: /*---------------------------------------------- Main Computation ---------------------------------------------------*/
294: #undef __FUNCT__
296: int MeshContextRun(MeshContext ctx)
297: {
298: int loop;
302: MeshContextSetup(ctx);
304: for(loop = 0; loop < ctx->numRefine; loop++) {
305: MeshContextRefineMesh(ctx);
306: }
307: for(loop = 0; loop < ctx->numCoarsen; loop++) {
308: MeshContextCoarsenMesh(ctx);
309: }
311: MeshContextCleanup(ctx);
312: return(0);
313: }