Mmg
Simplicial remeshers (mesh adaptation, isovalue discretization, lagrangian movement)
zaldy_2d.c
Go to the documentation of this file.
1/* =============================================================================
2** This file is part of the mmg software package for the tetrahedral
3** mesh modification.
4** Copyright (c) Bx INP/CNRS/Inria/UBordeaux/UPMC, 2004-
5**
6** mmg is free software: you can redistribute it and/or modify it
7** under the terms of the GNU Lesser General Public License as published
8** by the Free Software Foundation, either version 3 of the License, or
9** (at your option) any later version.
10**
11** mmg is distributed in the hope that it will be useful, but WITHOUT
12** ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13** FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
14** License for more details.
15**
16** You should have received a copy of the GNU Lesser General Public
17** License and of the GNU General Public License along with mmg (in
18** files COPYING.LESSER and COPYING). If not, see
19** <http://www.gnu.org/licenses/>. Please read their terms carefully and
20** use this copy of the mmg distribution only if you accept them.
21** =============================================================================
22*/
34#include "libmmg2d_private.h"
35
36
37/* Create a new vertex in the mesh, and return its number */
38MMG5_int MMG2D_newPt(MMG5_pMesh mesh,double c[2],int16_t tag) {
39 MMG5_pPoint ppt;
40 MMG5_int curpt;
41
42 if ( !mesh->npnil ) return 0;
43
44 curpt = mesh->npnil;
45 if ( mesh->npnil > mesh->np ) mesh->np = mesh->npnil;
46 ppt = &mesh->point[curpt];
47 memcpy(ppt->c,c,2*sizeof(double));
48 ppt->tag &= ~MG_NUL;
49 mesh->npnil = ppt->tmp;
50 ppt->tmp = 0;
51 ppt->tag = tag;
52
53 return curpt;
54}
55
56/* Delete a point in the mesh and update the garbage collector accordingly */
57void MMG2D_delPt(MMG5_pMesh mesh,MMG5_int ip) {
58 MMG5_pPoint ppt;
59
60 ppt = &mesh->point[ip];
61
62 memset(ppt,0,sizeof(MMG5_Point));
63 ppt->tag = MG_NUL;
64 ppt->tmp = mesh->npnil;
65
66 mesh->npnil = ip;
67 if ( ip == mesh->np ) mesh->np--;
68}
69
70void MMG5_delEdge(MMG5_pMesh mesh,MMG5_int iel) {
71 MMG5_pEdge pt;
72
73 pt = &mesh->edge[iel];
74 if ( !pt->a ) {
75 fprintf(stdout," ## INVALID EDGE.\n");
76 return;
77 }
78 memset(pt,0,sizeof(MMG5_Edge));
79 pt->b = mesh->nanil;
80 mesh->nanil = iel;
81 if ( iel == mesh->na ) mesh->na--;
82}
83
84/* Create a new triangle in the mesh and return its address */
86 MMG5_int curiel;
87
88 if ( !mesh->nenil ) {
89 return 0;
90 }
91 curiel = mesh->nenil;
92 if ( mesh->nenil > mesh->nt ) mesh->nt = mesh->nenil;
93 mesh->nenil = mesh->tria[curiel].v[2];
94 mesh->tria[curiel].v[2] = 0;
95 mesh->tria[curiel].ref = 0;
96 mesh->tria[curiel].base = 0;
97 mesh->tria[curiel].edg[0] = 0;
98 mesh->tria[curiel].edg[1] = 0;
99 mesh->tria[curiel].edg[2] = 0;
100
101 return curiel;
102}
103
104/* Delete a triangle in the mesh and update the garbage collector accordingly */
105int MMG2D_delElt(MMG5_pMesh mesh,MMG5_int iel) {
106 MMG5_pTria pt;
107 MMG5_int iadr;
108
109 pt = &mesh->tria[iel];
110 if ( !MG_EOK(pt) ) {
111 fprintf(stdout," ## INVALID ELEMENT.\n");
112 return 0;
113 }
114 memset(pt,0,sizeof(MMG5_Tria));
115 pt->v[2] = mesh->nenil;
116 pt->qual = 0.0;
117 iadr = (iel-1)*3 + 1;
118 if ( mesh->adja )
119 memset(&mesh->adja[iadr],0,3*sizeof(MMG5_int));
120
121 mesh->nenil = iel;
122 if ( iel == mesh->nt ) mesh->nt--;
123 return 1;
124}
125
141static inline
143 size_t usedMem,avMem,reservedMem,npadd;
144 int ctri,bytes;
145
147
148 /* init allocation need MMG5_MEMMIN B */
149 reservedMem = MMG5_MEMMIN + mesh->nquad*sizeof(MMG5_Quad);
150
151 /* Compute the needed initial memory */
152 usedMem = reservedMem + (mesh->np+1)*sizeof(MMG5_Point)
153 + (mesh->nt+1)*sizeof(MMG5_Tria) + (3*mesh->nt+1)*sizeof(MMG5_int)
154 + (mesh->na+1)*sizeof(MMG5_Edge) + (mesh->np+1)*sizeof(double);
155
156 if ( usedMem > mesh->memMax ) {
157 fprintf(stderr,"\n ## Error: %s: %zu MB of memory ",__func__,
159 fprintf(stderr,"is not enough to load mesh. You need to ask %zu MB minimum\n",
160 usedMem/MMG5_MILLION+1);
161 return 0;
162 }
163
164 ctri = 2;
165
166 /* Euler-poincare: ne = 6*np; nt = 2*np; na = np/5 *
167 * point+tria+edges+adjt+ aniso sol */
168 bytes = sizeof(MMG5_Point) +
169 2*sizeof(MMG5_Tria) + 3*2*sizeof(MMG5_int)
170 + 0.2*sizeof(MMG5_Edge) + 3*sizeof(double);
171
172 avMem = mesh->memMax-usedMem;
173
174 /* If npadd is exactly the maximum memory available, we will use all the
175 * memory and the analysis step will fail. As arrays may be reallocated, we
176 * can have smaller values for npmax and ntmax (npadd/2). */
177 npadd = avMem/(2*bytes);
178 mesh->npmax = MG_MIN(mesh->npmax,mesh->np+npadd);
179 mesh->ntmax = MG_MIN(mesh->ntmax,ctri*npadd+mesh->nt);
180 mesh->namax = MG_MIN(mesh->namax,ctri*npadd+mesh->na);
181
182 if ( sizeof(MMG5_int) == sizeof(int32_t) ) {
185 int coef;
186 if ( mesh->nquad ) {
187 coef = 4;
188 }
189 else {
190 coef = 3;
191 }
192
193 /* maximal number of triangles, taking the
194 * computation of adjacency relationships into account */
195 int32_t int32_ntmax = (INT32_MAX-(coef+1))/coef;
196
197 if ( int32_ntmax < mesh->ntmax ) {
198 if ( int32_ntmax <= mesh->nt ) {
199 /* No possible allocation without int32 overflow */
200 fprintf(stderr,"\n ## Error: %s: with %" MMG5_PRId " triangles Mmg will overflow"
201 " the 32-bit integer.\n",__func__,mesh->nt);
202 fprintf(stderr,"Please, configure Mmg with MMG5_INT=int64_t argument.\n");
203 return 0;
204 }
205 else {
206 /* Correction of maximal number of triangles */
207 mesh->ntmax = int32_ntmax;
208 }
209 }
210 }
211
212 if ( abs(mesh->info.imprim) > 4 || mesh->info.ddebug ) {
213 fprintf(stdout," MAXIMUM MEMORY AUTHORIZED (MB) %zu\n",
215 }
216
217 if ( abs(mesh->info.imprim) > 5 || mesh->info.ddebug ) {
218 fprintf(stdout," MMG2D_NPMAX %" MMG5_PRId "\n",mesh->npmax);
219 fprintf(stdout," MMG2D_NTMAX %" MMG5_PRId "\n",mesh->ntmax);
220 }
221
222 return 1;
223}
224
234
236
239 mesh->namax = mesh->na;
240
242}
243
253 MMG5_int k;
254
255 MMG5_ADD_MEM(mesh,(mesh->npmax+1)*sizeof(MMG5_Point),"initial vertices",
256 printf(" Exit program.\n");
257 return 0);
259
260 MMG5_ADD_MEM(mesh,(mesh->ntmax+1)*sizeof(MMG5_Tria),"initial triangles",return 0);
262 memset(&mesh->tria[0],0,sizeof(MMG5_Tria));
263
264 if ( mesh->nquad ) {
265 MMG5_ADD_MEM(mesh,(mesh->nquad+1)*sizeof(MMG5_Quad),"initial quadrilaterals",return 0);
267 }
268
269 mesh->namax = mesh->na;
270 if ( mesh->na ) {
271 MMG5_ADD_MEM(mesh,(mesh->namax+1)*sizeof(MMG5_Edge),"initial edges",return 0);
273 }
274
275 /* keep track of empty links */
276 mesh->npnil = mesh->np + 1;
277 mesh->nenil = mesh->nt + 1;
278 mesh->nanil = 0;
279
280 for (k=mesh->npnil; k<mesh->npmax-1; k++) {
281 /* Set tangent field of point to 0 */
282 mesh->point[k].n[0] = 0;
283 mesh->point[k].n[1] = 0;
284 mesh->point[k].n[2] = 0;
285 /* link */
286 mesh->point[k].tmp = k+1;
287 }
288
289 for (k=mesh->nenil; k<mesh->ntmax-1; k++)
290 mesh->tria[k].v[2] = k+1;
291
292 return 1;
293}
294
304
305 if ( !MMG2D_memOption(mesh) ) return 0;
306
308}
MMG5_pMesh * mesh
#define MMG2D_NPMAX
#define MMG2D_NEMAX
#define MMG5_SAFE_CALLOC(ptr, size, type, law)
size_t MMG5_memSize(void)
Definition: tools.c:852
#define MG_EOK(pt)
void MMG5_memOption_memSet(MMG5_pMesh mesh)
Definition: tools.c:891
#define MG_NUL
#define MG_MIN(a, b)
#define MG_MAX(a, b)
#define MMG5_ADD_MEM(mesh, size, message, law)
#define MMG5_MILLION
#define MMG5_MEMMIN
Structure to store edges of a MMG mesh.
Definition: libmmgtypes.h:305
MMG5_int b
Definition: libmmgtypes.h:306
MMG5_int a
Definition: libmmgtypes.h:306
int8_t ddebug
Definition: libmmgtypes.h:532
MMG mesh structure.
Definition: libmmgtypes.h:605
MMG5_int ntmax
Definition: libmmgtypes.h:612
MMG5_pQuad quadra
Definition: libmmgtypes.h:648
MMG5_Info info
Definition: libmmgtypes.h:651
MMG5_pPoint point
Definition: libmmgtypes.h:641
MMG5_int * adja
Definition: libmmgtypes.h:624
MMG5_int nquad
Definition: libmmgtypes.h:613
size_t memMax
Definition: libmmgtypes.h:606
MMG5_int npmax
Definition: libmmgtypes.h:612
MMG5_int nenil
Definition: libmmgtypes.h:622
MMG5_int namax
Definition: libmmgtypes.h:612
MMG5_int nt
Definition: libmmgtypes.h:612
MMG5_pTria tria
Definition: libmmgtypes.h:647
MMG5_int np
Definition: libmmgtypes.h:612
MMG5_pEdge edge
Definition: libmmgtypes.h:649
MMG5_int nanil
Definition: libmmgtypes.h:623
MMG5_int na
Definition: libmmgtypes.h:612
MMG5_int npnil
Definition: libmmgtypes.h:621
Structure to store points of a MMG mesh.
Definition: libmmgtypes.h:270
double n[3]
Definition: libmmgtypes.h:272
int16_t tag
Definition: libmmgtypes.h:284
MMG5_int tmp
Definition: libmmgtypes.h:280
double c[3]
Definition: libmmgtypes.h:271
MMG5_int edg[3]
Definition: libmmgtypes.h:339
double qual
Definition: libmmgtypes.h:333
MMG5_int ref
Definition: libmmgtypes.h:335
MMG5_int base
Definition: libmmgtypes.h:336
MMG5_int v[3]
Definition: libmmgtypes.h:334
void MMG5_delEdge(MMG5_pMesh mesh, MMG5_int iel)
Definition: zaldy_2d.c:70
int MMG2D_memOption(MMG5_pMesh mesh)
Definition: zaldy_2d.c:233
static int MMG2D_memOption_memSet(MMG5_pMesh mesh)
Definition: zaldy_2d.c:142
int MMG2D_zaldy(MMG5_pMesh mesh)
Definition: zaldy_2d.c:303
int MMG2D_delElt(MMG5_pMesh mesh, MMG5_int iel)
Definition: zaldy_2d.c:105
void MMG2D_delPt(MMG5_pMesh mesh, MMG5_int ip)
Definition: zaldy_2d.c:57
MMG5_int MMG2D_newPt(MMG5_pMesh mesh, double c[2], int16_t tag)
Definition: zaldy_2d.c:38
int MMG2D_setMeshSize_alloc(MMG5_pMesh mesh)
Definition: zaldy_2d.c:252
MMG5_int MMG2D_newElt(MMG5_pMesh mesh)
Definition: zaldy_2d.c:85