20 #define _XOPEN_SOURCE 600 28 struct FmsMesh_private {
47 struct FmsDomain_private {
70 struct _FmsPart_private {
82 struct FmsComponent_private {
89 struct _FmsPart_private *parts;
94 struct FmsTag_private {
97 FmsInt num_tag_descriptions;
101 void *described_tags;
102 char **tag_descriptions;
105 struct FmsMetaData_private {
117 struct _FmsFieldDescriptor_FixedOrder {
123 struct FmsFieldDescriptor_private {
129 struct _FmsFieldDescriptor_FixedOrder *fixed_order;
134 struct FmsField_private {
144 struct FmsDataCollection_private {
155 1, 2, 4, 8, 1, 2, 4, 8
181 0, 1, 2, 2, 3, 3, 3, 3
185 0, 2, 3, 4, 4, 6, 5, 5
189 1, 2, 3, 4, 4, 8, 6, 5
193 sizeof(float),
sizeof(
double), 2*
sizeof(float), 2*
sizeof(
double)
200 "FMS_COMPLEX_DOUBLE",
216 #define E_RETURN(code) return (code) 218 static void FmsErrorDebug(
int err_code,
const char *func,
const char *file,
221 "\n\nFMS error encountered!\n" 225 "Aborting ...\n\n", err_code, func, file, line);
232 #if defined(__clang__) 233 #define FMS_PRETTY_FUNCTION __PRETTY_FUNCTION__ 234 #elif !defined(_MSC_VER) 235 #define FMS_PRETTY_FUNCTION __func__ 236 #else // for Visual Studio C++ 237 #define FMS_PRETTY_FUNCTION __FUNCSIG__ 239 #define E_RETURN(code) \ 242 FmsErrorDebug(code, FMS_PRETTY_FUNCTION, __FILE__, __LINE__); \ 248 static int UpdateError(
int old_err,
int new_err) {
249 return old_err ? old_err : new_err;
253 return (a <= b) ? a : b;
257 return (a >= b) ? a : b;
263 while (m < n) { m *= 2; }
267 static void FmsAbortNotImplemented() {
268 fprintf(stderr,
"\n\nNot implemented! Aborting ...\n\n");
273 static void FmsInternalError() {
274 fprintf(stderr,
"\n\nFMS internal error detected! Aborting ...\n\n");
279 static inline int FmsCopyString(
const char *str,
char **str_copy_p) {
280 if (str == NULL) { *str_copy_p = NULL;
return 0; }
281 char *str_copy = strdup(str);
282 if (str_copy == NULL) {
return 1; }
283 *str_copy_p = str_copy;
288 #define FMS_ICC_IL(src_t,src,dst_t,dst,size) \ 290 for (FmsInt idx = 0; idx < (size); idx++) { \ 291 ((dst_t*)(dst))[idx] = (dst_t)(((src_t*)(src))[idx]); \ 296 #define FMS_ICC_SW(src_type,src,dst_t,dst,size) \ 297 switch (src_type) { \ 298 case FMS_INT8: FMS_ICC_IL( int8_t,src,dst_t,dst,size); break; \ 299 case FMS_INT16: FMS_ICC_IL( int16_t,src,dst_t,dst,size); break; \ 300 case FMS_INT32: FMS_ICC_IL( int32_t,src,dst_t,dst,size); break; \ 301 case FMS_INT64: FMS_ICC_IL( int64_t,src,dst_t,dst,size); break; \ 302 case FMS_UINT8: FMS_ICC_IL( uint8_t,src,dst_t,dst,size); break; \ 303 case FMS_UINT16: FMS_ICC_IL(uint16_t,src,dst_t,dst,size); break; \ 304 case FMS_UINT32: FMS_ICC_IL(uint32_t,src,dst_t,dst,size); break; \ 305 case FMS_UINT64: FMS_ICC_IL(uint64_t,src,dst_t,dst,size); break; \ 306 default: FmsAbortNotImplemented(); \ 311 static int FmsIntConvertCopy(
FmsIntType src_type,
const void *src,
325 default: FmsAbortNotImplemented();
331 #define FMS_IPCC_IL(src_t,src,dst_t,dst,tuple_size,perm,tot_size) \ 333 for (FmsInt i = 0; i < (tot_size); i += (tuple_size)) { \ 334 src_t *loc_src = (src_t*)(src) + i; \ 335 dst_t *loc_dst = (dst_t*)(dst) + i; \ 336 for (FmsInt j = 0; j < (tuple_size); j++) { \ 337 loc_dst[j] = (dst_t)(loc_src[perm[j]]); \ 343 #define FMS_IPCC_SW(src_type,src,dst_t,dst,ts,perm,size) \ 344 switch (src_type) { \ 345 case FMS_INT8: FMS_IPCC_IL( int8_t,src,dst_t,dst,ts,perm,size); break; \ 346 case FMS_INT16: FMS_IPCC_IL( int16_t,src,dst_t,dst,ts,perm,size); break; \ 347 case FMS_INT32: FMS_IPCC_IL( int32_t,src,dst_t,dst,ts,perm,size); break; \ 348 case FMS_INT64: FMS_IPCC_IL( int64_t,src,dst_t,dst,ts,perm,size); break; \ 349 case FMS_UINT8: FMS_IPCC_IL( uint8_t,src,dst_t,dst,ts,perm,size); break; \ 350 case FMS_UINT16: FMS_IPCC_IL(uint16_t,src,dst_t,dst,ts,perm,size); break; \ 351 case FMS_UINT32: FMS_IPCC_IL(uint32_t,src,dst_t,dst,ts,perm,size); break; \ 352 case FMS_UINT64: FMS_IPCC_IL(uint64_t,src,dst_t,dst,ts,perm,size); break; \ 353 default: FmsAbortNotImplemented(); \ 359 static int FmsIntPermuteConvertCopy(
FmsIntType src_type,
const void *src,
361 const int *perm,
FmsInt tuple_size,
366 if (tuple_size == 0 || tot_size % tuple_size != 0) {
E_RETURN(2); }
367 const FmsInt ts = tuple_size;
377 default: FmsAbortNotImplemented();
383 #define FMS_IMC_IL(src_t,src,dst_t,dst,map,size) \ 385 for (FmsInt idx = 0; idx < (size); idx++) { \ 386 ((dst_t*)(dst))[idx] = ((dst_t*)(map))[((src_t*)(src))[idx]]; \ 391 #define FMS_IMC_SW(src_type,src,dst_t,dst,map,size) \ 392 switch (src_type) { \ 393 case FMS_INT8: FMS_IMC_IL( int8_t,src,dst_t,dst,map,size); break; \ 394 case FMS_INT16: FMS_IMC_IL( int16_t,src,dst_t,dst,map,size); break; \ 395 case FMS_INT32: FMS_IMC_IL( int32_t,src,dst_t,dst,map,size); break; \ 396 case FMS_INT64: FMS_IMC_IL( int64_t,src,dst_t,dst,map,size); break; \ 397 case FMS_UINT8: FMS_IMC_IL( uint8_t,src,dst_t,dst,map,size); break; \ 398 case FMS_UINT16: FMS_IMC_IL(uint16_t,src,dst_t,dst,map,size); break; \ 399 case FMS_UINT32: FMS_IMC_IL(uint32_t,src,dst_t,dst,map,size); break; \ 400 case FMS_UINT64: FMS_IMC_IL(uint64_t,src,dst_t,dst,map,size); break; \ 401 default: FmsAbortNotImplemented(); \ 405 static int FmsIntMapCopy(
FmsIntType src_type,
const void *src,
406 FmsIntType dst_type,
void *dst,
const void *map,
420 default: FmsAbortNotImplemented();
426 #define FMS_E2S_TEMPL(idx_t) \ 428 const idx_t *ents_ = (idx_t*)ents + loc_side_begin; \ 429 const idx_t *sides_ = sides; \ 430 for (FmsInt ent_id = 0; ent_id < num_ents; ent_id++) { \ 431 const idx_t *ent_off = &ents_[ent_id*ent_sides]; \ 432 FmsInt *res_ent = &res_[ent_id*res_stride]; \ 433 for (FmsInt loc_off = 0; loc_off < num_loc_sides; loc_off++) { \ 434 const idx_t side_id = ent_off[loc_off]; \ 435 const idx_t *side = &sides_[side_id*side_sides]; \ 436 FmsInt *res_side = &res_ent[loc_off*side_sides]; \ 437 for (FmsInt ss_id = 0; ss_id < side_sides; ss_id++) { \ 438 res_side[ss_id] = side[ss_id]; \ 449 const void *ents,
FmsInt side_sides,
450 const void *sides,
FmsInt res_stride,
453 FmsInt *res_ = res + res_off;
463 default: FmsAbortNotImplemented();
468 static inline int FmsIntersectTwoEdges(
FmsInt *edge1,
FmsInt *edge2,
471 if (edge1[0] == edge2[0] || edge1[0] == edge2[1]) {
472 *v_common = edge1[0];
475 if (edge1[0] != edge1[1]) {
476 if (edge1[1] == edge2[0] || edge1[1] == edge2[1]) {
477 *v_common = edge1[1];
484 static int FmsOrientFaceSides(
FmsInt num_sides,
FmsInt num_faces,
496 const int n = num_sides;
497 for (
FmsInt k = 0; k < num_faces; k++) {
499 for (
int i = 0; i < n; i++) {
500 nc[i] = FmsIntersectTwoEdges(face_verts+2*((i+n-1)%n),
501 face_verts+2*i, vi+i);
504 for (
int ei = 0; ei < n; ei++) {
506 if (face_verts[2*ei+0] == face_verts[2*ei+1] ||
507 (nc[ei] != 1 && nc[ej] != 1)) {
512 orientations[ei] = (vi[ei] == face_verts[2*ei+0]) ? 0 : 1;
514 orientations[ei] = (vi[ej] == face_verts[2*ei+1]) ? 0 : 1;
525 FmsInt a0 = a[0], a1 = a[1], a2 = a[2];
562 FmsInt a0 = a[0], a1 = a[1];
616 static inline int FmsIntersectSorted(
int n1,
int n2,
FmsInt *face1,
619 FmsInt e1 = face1[0], e2 = face2[0];
620 for (
int i1 = 0, i2 = 0; 1; ) {
625 if (++i2 == n2) {
return num_common; }
629 if (++i1 == n1) {
return num_common; }
632 }
else if (e1 < e2) {
634 if (++i1 == n1) {
return num_common; }
639 if (++i2 == n2) {
return num_common; }
658 if (be[0] == be[1] || be[0] == be[2] || be[1] == be[2]) {
663 while (ee[0] != be[i0]) {
666 if (i0 == 3) { FmsInternalError(); }
671 return (be[(i0+1)%3] == ee[1]) ? 2*i0 : 2*i0+1;
672 }
else if (ne[2] == 1) {
674 return (be[(i0+2)%3] == ee[2]) ? 2*i0 : 2*i0+1;
676 }
else if (ne[1] == 1 && ne[2] == 1) {
679 while (ee[1] != be[i1]) {
682 if (i1 == 3) { FmsInternalError(); }
685 if (be[(i1+1)%3] == ee[2]) {
709 if (se[0] == se[1] || se[1] == se[2] || se[2] == se[3]) {
715 if (ne[0] != 1 || ne[1] != 1 || ne[2] != 1 || ne[3] != 1) {
719 while (ee[0] != be[i0]) {
722 if (i0 == 4) { FmsInternalError(); }
726 return (be[(i0+1)%4] == ee[1]) ? 2*i0 : 2*i0+1;
729 static int FmsOrientTetSides(
FmsInt num_tets,
FmsInt *tet_edges,
731 for (
FmsInt i = 0; i < num_tets; i++) {
732 FmsInt tet_edges_sorted[4][3];
733 for (
int loc_face_id = 0; loc_face_id < 4; loc_face_id++) {
734 Sort3(tet_edges+3*loc_face_id, tet_edges_sorted[loc_face_id]);
741 static const int tet_edge_face[6][2] = {
744 {0, 1}, {0, 3}, {0, 2}, {1, 2}, {1, 3}, {2, 3}
748 static const int tet_face_edge[4][3] = {
750 {0, 2, 1}, {0, 4, 3}, {2, 3, 5}, {1, 5, 4}
754 for (
int i = 0; i < 6; i++) {
755 const int *f = tet_edge_face[i];
756 nc[i] = FmsIntersectSorted(3, 3, tet_edges_sorted[f[0]],
757 tet_edges_sorted[f[1]], ei+i);
762 for (
int loc_face_id = 0; loc_face_id < 4; loc_face_id++) {
763 const int *e = tet_face_edge[loc_face_id];
764 int ne[3] = { nc[e[0]], nc[e[1]], nc[e[2]] };
765 FmsInt ee[3] = { ei[e[0]], ei[e[1]], ei[e[2]] };
766 FmsInt *be = tet_edges+3*loc_face_id;
770 orientations[loc_face_id] = ori;
782 static int FmsOrientHexSides(
FmsInt num_hexes,
FmsInt *hex_edges,
784 for (
FmsInt i = 0; i < num_hexes; i++) {
785 FmsInt hex_edges_sorted[6][4];
786 for (
int loc_face_id = 0; loc_face_id < 6; loc_face_id++) {
787 Sort4(hex_edges+4*loc_face_id, hex_edges_sorted[loc_face_id]);
794 static const int hex_edge_face[12][2] = {
798 {0, 2}, {0, 5}, {0, 3}, {0, 4}, {1, 2}, {1, 5},
799 {1, 3}, {1, 4}, {2, 4}, {2, 5}, {3, 5}, {3, 4}
803 static const int hex_face_edge[6][4] = {
805 {0, 3, 2, 1}, {4, 5, 6, 7}, {0, 9, 4, 8},
806 {2, 11, 6, 10}, {3, 8, 7, 11}, {1, 10, 5, 9}
810 for (
int i = 0; i < 12; i++) {
811 const int *f = hex_edge_face[i];
812 nc[i] = FmsIntersectSorted(4, 4, hex_edges_sorted[f[0]],
813 hex_edges_sorted[f[1]], ei+i);
818 for (
int loc_face_id = 0; loc_face_id < 6; loc_face_id++) {
819 const int *e = hex_face_edge[loc_face_id];
820 int ne[4] = { nc[e[0]], nc[e[1]], nc[e[2]], nc[e[3]] };
821 FmsInt ee[4] = { ei[e[0]], ei[e[1]], ei[e[2]], ei[e[3]] };
822 FmsInt *be = hex_edges+4*loc_face_id;
825 GetQuadOrientation(ne, ee, be, hex_edges_sorted[loc_face_id]);
827 orientations[loc_face_id] = ori;
843 static const int tri_perm[6][3] = {
844 {0, 1, 2}, {0, 2, 1}, {1, 2, 0}, {1, 0, 2}, {2, 0, 1}, {2, 1, 0}
846 const int *perm = tri_perm[ori];
847 for (
int i = 0; i < 3; i++) {
848 e_out[i] = e_in[perm[i]];
856 static const int quad_perm[8][4] = {
857 {0, 1, 2, 3}, {0, 3, 2, 1}, {1, 2, 3, 0}, {1, 0, 3, 2},
858 {2, 3, 0, 1}, {2, 1, 0, 3}, {3, 0, 1, 2}, {3, 2, 1, 0}
860 const int *perm = quad_perm[ori];
861 for (
int i = 0; i < 4; i++) {
862 e_out[i] = e_in[perm[i]];
973 m = calloc(1,
sizeof(*m));
975 m->num_partitions = 1;
983 for (
FmsInt domain_id = 0; domain_id < mesh->num_domains; domain_id++) {
984 FmsDomain domain = mesh->domains[domain_id];
988 const FmsIntType side_ids_type = domain->side_ids_type[et];
991 const FmsInt num_tri = domain->num_entities[et];
992 const char *all_tris = domain->entities[et];
993 const void *all_edges = domain->entities[
FMS_EDGE];
995 const int bsize = 1024;
996 FmsInt tri_verts[6*bsize];
997 for (
FmsInt off = 0; off < num_tri; off += bsize) {
998 const FmsInt sz = FmsIntMin(bsize, num_tri-off);
999 FmsEntitiesToSides(side_ids_type, 3, 0, 3, all_tris, 2, all_edges,
1000 6, 0, tri_verts, sz);
1001 int err = FmsOrientFaceSides(3, sz, tri_verts, oris);
1004 all_tris += 3*sz*sizeof_side_ids;
1011 const FmsIntType side_ids_type = domain->side_ids_type[et];
1014 const FmsInt num_quads = domain->num_entities[et];
1015 const char *all_quads = domain->entities[et];
1016 const void *all_edges = domain->entities[
FMS_EDGE];
1018 const int bsize = 1024;
1019 FmsInt quad_verts[8*bsize];
1020 for (
FmsInt off = 0; off < num_quads; off += bsize) {
1021 const FmsInt sz = FmsIntMin(bsize, num_quads-off);
1022 FmsEntitiesToSides(side_ids_type, 4, 0, 4, all_quads, 2, all_edges,
1023 8, 0, quad_verts, sz);
1024 int err = FmsOrientFaceSides(4, sz, quad_verts, oris);
1027 all_quads += 4*sz*sizeof_side_ids;
1034 const FmsIntType side_ids_type = domain->side_ids_type[et];
1037 const FmsInt num_tets = domain->num_entities[et];
1038 const char *all_tets = domain->entities[et];
1041 const int bsize = 512;
1042 FmsInt tet_edges[12*bsize];
1043 for (
FmsInt off = 0; off < num_tets; off += bsize) {
1044 const FmsInt sz = FmsIntMin(bsize, num_tets-off);
1045 FmsEntitiesToSides(side_ids_type, 4, 0, 4, all_tets, 3, all_tris,
1046 12, 0, tet_edges, sz);
1047 int err = FmsOrientTetSides(sz, tet_edges, oris);
1050 all_tets += 4*sz*sizeof_side_ids;
1057 const FmsIntType side_ids_type = domain->side_ids_type[et];
1062 const FmsInt num_hexes = domain->num_entities[et];
1063 const char *all_hexes = domain->entities[et];
1066 const int bsize = 256;
1067 FmsInt hex_edges[24*bsize];
1068 for (
FmsInt off = 0; off < num_hexes; off += bsize) {
1069 const FmsInt sz = FmsIntMin(bsize, num_hexes-off);
1070 FmsEntitiesToSides(side_ids_type, 6, 0, 6, all_hexes, 4, all_quads,
1071 24, 0, hex_edges, sz);
1072 int err = FmsOrientHexSides(sz, hex_edges, oris);
1075 all_hexes += 6*sz*sizeof_side_ids;
1082 FmsAbortNotImplemented();
1087 FmsAbortNotImplemented();
1097 if (mesh->domain_offsets[0] != 0) {
E_RETURN(2); }
1098 if (mesh->domain_offsets[mesh->num_domain_names] != mesh->num_domains) {
1101 if (mesh->partition_id >= mesh->num_partitions) {
E_RETURN(4); }
1103 for (
FmsInt name_id = 0; name_id < mesh->num_domain_names; name_id++) {
1104 const FmsInt name_start = mesh->domain_offsets[name_id];
1105 const FmsInt name_end = mesh->domain_offsets[name_id+1];
1106 for (
FmsInt domain_id = name_start; domain_id < name_end; domain_id++) {
1107 FmsDomain domain = mesh->domains[domain_id];
1108 if (domain->name != mesh->domain_names[name_id]) {
E_RETURN(5); }
1109 if (name_start + domain->id != domain_id) {
E_RETURN(6); }
1114 char **domain_names = mesh->domain_names;
1115 for (
FmsInt comp_id = 0; comp_id < mesh->num_comps; comp_id++) {
1117 if (comp->id != comp_id) {
E_RETURN(7); }
1119 for (
FmsInt part_id = 0; part_id < comp->num_parts; part_id++) {
1120 FmsDomain domain = comp->parts[part_id].domain;
1121 FmsInt domain_name_id = 0;
1122 for ( ; 1; domain_name_id++) {
1123 if (domain_name_id == mesh->num_domain_names) {
E_RETURN(9); }
1124 if (strcmp(domain->name, domain_names[domain_name_id]) == 0) {
break; }
1126 FmsInt b_offset = mesh->domain_offsets[domain_name_id];
1127 FmsInt num_domains = mesh->domain_offsets[domain_name_id+1] - b_offset;
1128 if (domain->id >= num_domains) {
E_RETURN(10); }
1129 if (mesh->domains[b_offset + domain->id] != domain) {
E_RETURN(11); }
1133 for (
FmsInt tag_id = 0; tag_id < mesh->num_tags; tag_id++) {
1134 FmsTag tag = mesh->tags[tag_id];
1135 FmsInt comp_id = tag->comp->id;
1136 if (comp_id >= mesh->num_comps) {
E_RETURN(12); }
1137 if (mesh->comps[comp_id] != tag->comp) {
E_RETURN(13); }
1147 for (
FmsInt i = 0; i < m->num_domains; i++) {
1150 free(domain->orientations[j]);
1151 free(domain->entities[j]);
1158 for (
FmsInt i = 0; i < m->num_comps; i++) {
1160 free(comp->relations);
1163 for (
FmsInt j = 0; j < comp->num_parts; j++) {
1164 struct _FmsPart_private *part = &comp->parts[j];
1166 free(part->orientations[k]);
1167 free(part->entities_ids[k]);
1176 for (
FmsInt i = 0; i < m->num_tags; i++) {
1178 for (
FmsInt j = 0; j < tag->num_tag_descriptions; j++) {
1179 free(tag->tag_descriptions[j]);
1181 free(tag->tag_descriptions);
1182 free(tag->described_tags);
1189 for (
FmsInt i = 0; i < m->num_domain_names; i++) {
1190 free(m->domain_names[i]);
1192 free(m->domain_names);
1193 free(m->domain_offsets);
1205 if (partition_id >= num_partitions) {
E_RETURN(2); }
1206 mesh->partition_id = partition_id;
1207 mesh->num_partitions = num_partitions;
1216 FmsInt num_domain_names = mesh->num_domain_names;
1217 char **domain_names = mesh->domain_names;
1219 for (
FmsInt i = 0; i < num_domain_names; i++) {
1220 if (strcmp(domain_name, domain_names[i]) == 0) {
E_RETURN(4); }
1222 FmsInt *domain_offsets = mesh->domain_offsets;
1224 FmsInt nc = NextPow2(num_domain_names+1);
1225 if (num_domain_names <= nc/2) {
1226 domain_names = realloc(domain_names, nc*
sizeof(*domain_names));
1227 if (domain_names == NULL) {
E_RETURN(5); }
1228 mesh->domain_names = domain_names;
1229 domain_offsets = realloc(domain_offsets, (nc+1)*
sizeof(
FmsInt));
1230 if (domain_offsets == NULL) {
E_RETURN(5); }
1231 domain_offsets[0] = 0;
1232 mesh->domain_offsets = domain_offsets;
1235 const FmsInt m_num_domains = mesh->num_domains;
1237 if (num_domains != 0) {
1238 nc = NextPow2(m_num_domains + num_domains);
1239 if (m_num_domains <= nc/2) {
1240 m_domains = realloc(m_domains, nc*
sizeof(
FmsDomain));
1241 if (m_domains == NULL) {
E_RETURN(5); }
1242 mesh->domains = m_domains;
1245 char *domain_name_copy;
1246 if (FmsCopyString(domain_name, &domain_name_copy)) {
E_RETURN(5); }
1248 for (
FmsInt i = 0; i < num_domains; i++) {
1250 domain = calloc(1,
sizeof(*domain));
1251 if (domain == NULL) {
1252 while (i != 0) { free(m_domains[m_num_domains + (--i)]); }
1253 free(domain_name_copy);
1257 domain->name = domain_name_copy;
1260 m_domains[m_num_domains + i] = domain;
1262 domain_names[num_domain_names] = domain_name_copy;
1263 mesh->num_domain_names = ++num_domain_names;
1264 mesh->num_domains = domain_offsets[num_domain_names] = m_num_domains +
1266 *domains = m_domains + m_num_domains;
1274 FmsInt num_comps = mesh->num_comps;
1277 FmsInt nc = NextPow2(num_comps+1);
1278 if (num_comps <= nc/2) {
1279 comps = realloc(comps, nc*
sizeof(*comps));
1280 if (comps == NULL) {
E_RETURN(3); }
1281 mesh->comps = comps;
1284 component = calloc(1,
sizeof(*component));
1285 if (component == NULL) {
E_RETURN(3); }
1287 if (FmsCopyString(comp_name, &component->name)) {
1290 component->id = num_comps;
1292 comps[num_comps] = component;
1293 mesh->num_comps = num_comps+1;
1301 FmsInt num_tags = mesh->num_tags;
1302 FmsTag *tags = mesh->tags;
1304 FmsInt nc = NextPow2(num_tags+1);
1305 if (num_tags <= nc/2) {
1306 tags = realloc(tags, nc*
sizeof(*tags));
1311 t = calloc(1,
sizeof(*t));
1314 if (FmsCopyString(tag_name, &t->name)) { free(t);
E_RETURN(3); }
1317 mesh->num_tags = num_tags+1;
1329 domain->num_entities[
FMS_VERTEX] = num_verts;
1339 domain->num_entities[type] = num_ents;
1346 domain->num_entities[type] = 0;
1347 domain->entities_caps[type] = 0;
1348 free(domain->orientations[type]);
1349 free(domain->entities[type]);
1350 if (num_ents != 0) {
1351 FmsInt tot_sides = num_ents*num_sides;
1352 domain->entities[type] = malloc(tot_sides*sizeof_side_ids);
1353 if (domain->entities[type] == NULL) {
1354 domain->orientations[type] = NULL;
1357 domain->orientations[type] = malloc(tot_sides*
sizeof(
FmsOrientation));
1358 if (domain->orientations[type] == NULL) {
1359 free(domain->entities[type]);
1360 domain->entities[type] = NULL;
1364 for (
FmsInt i = 0; i < tot_sides; i++) {
1368 domain->entities[type] = NULL;
1369 domain->orientations[type] = NULL;
1371 domain->entities_caps[type] = num_ents;
1372 domain->side_ids_type[type] = id_store_type;
1376 domain->dim = FmsIntMax(domain->dim,
FmsEntityDim[type]);
1388 domain->num_entities[type] = domain->entities_caps[type];
1389 *ents = domain->entities[type];
1397 if (side_orients == NULL) {
E_RETURN(3); }
1398 *side_orients = domain->orientations[type];
1404 const void *ents,
FmsInt num_ents) {
1407 const FmsInt num_entities = domain->num_entities[type];
1408 if (num_entities + num_ents > domain->entities_caps[type]) {
E_RETURN(3); }
1409 const FmsIntType side_ids_type = domain->side_ids_type[type];
1412 void *ents_dst = (
char*)(domain->entities[type]) +
1413 num_entities*num_sides*sizeof_side_ids;
1414 const int *perm = reordering ? reordering[type] : NULL;
1416 FmsIntConvertCopy(ent_id_type, ents, side_ids_type, ents_dst,
1417 num_ents*num_sides);
1419 FmsIntPermuteConvertCopy(ent_id_type, ents, side_ids_type, ents_dst,
1420 perm, num_sides, num_ents*num_sides);
1422 domain->num_entities[type] = num_entities + num_ents;
1430 if (ent_id >= domain->entities_caps[type]) {
E_RETURN(3); }
1432 if (loc_side_id >= num_sides) {
E_RETURN(4); }
1434 orientations[ent_id*num_sides + loc_side_id] = side_orient;
1446 const FmsInt num_parts = comp->num_parts;
1447 const FmsInt comp_dim = comp->dim;
1448 const FmsInt dim = domain->dim;
1450 struct _FmsPart_private *parts = comp->parts;
1452 FmsInt nc = NextPow2(num_parts + 1);
1453 if (num_parts <= nc/2) {
1454 parts = realloc(parts, nc*
sizeof(*parts));
1455 if (parts == NULL) {
E_RETURN(4); }
1456 comp->parts = parts;
1458 struct _FmsPart_private *part = parts + num_parts;
1460 memset(part, 0,
sizeof(*part));
1461 part->domain = domain;
1462 FmsInt num_main_entities = comp->num_main_entities;
1464 FmsInt num_entities = domain->num_entities[t];
1465 part->num_entities[t] = num_entities;
1467 num_main_entities += num_entities;
1477 comp->num_main_entities = num_main_entities;
1478 comp->num_parts = num_parts + 1;
1486 const FmsInt num_parts = comp->num_parts;
1487 struct _FmsPart_private *parts = comp->parts;
1489 FmsInt nc = NextPow2(num_parts + 1);
1490 if (num_parts <= nc/2) {
1491 parts = realloc(parts, nc*
sizeof(*parts));
1492 if (parts == NULL) {
E_RETURN(4); }
1493 comp->parts = parts;
1495 struct _FmsPart_private *part = parts + num_parts;
1497 memset(part, 0,
sizeof(*part));
1498 part->domain = domain;
1499 comp->num_parts = num_parts + 1;
1500 *part_id = num_parts;
1508 const void *ents,
const void *ent_orients,
1511 if (part_id >= comp->num_parts) {
E_RETURN(2); }
1519 struct _FmsPart_private *part = comp->parts + part_id;
1520 const FmsInt num_entities = part->num_entities[type];
1521 void *entities_ids = part->entities_ids[type];
1523 if (num_entities != 0) {
1524 if (entities_ids == NULL) {
E_RETURN(7); }
1525 if (orientations == NULL) {
E_RETURN(8); }
1527 if (ent_orients == NULL) {
E_RETURN(10); }
1528 if (part->entities_ids_type[type] != id_store_type) {
E_RETURN(11); }
1529 }
else if (ents == NULL) {
1530 if (num_ents != part->domain->num_entities[type]) {
E_RETURN(12); }
1533 if (num_ents != 0) {
1534 const FmsInt nc = NextPow2(num_entities + num_ents);
1536 if (num_entities <= nc/2) {
1537 entities_ids = realloc(entities_ids, nc*sizeof_ent_ids);
1538 if (entities_ids == NULL) {
E_RETURN(13); }
1539 part->entities_ids[type] = entities_ids;
1541 FmsIntConvertCopy(ent_id_type, ents, id_store_type,
1542 (
char*)entities_ids + num_entities*sizeof_ent_ids,
1547 if (ent_orients != NULL) {
1548 if (num_entities <= nc/2) {
1550 if (orientations == NULL) {
E_RETURN(13); }
1551 part->orientations[type] = orientations;
1553 if (inv_orient_map != NULL) {
1555 orientations + num_entities, inv_orient_map, num_ents);
1558 orientations + num_entities, num_ents);
1565 part->num_entities[type] = num_entities + num_ents;
1566 if (num_entities == 0) {
1567 part->entities_ids_type[type] = id_store_type;
1573 comp->num_main_entities += num_ents;
1582 if (part_id >= comp->num_parts) {
E_RETURN(2); }
1589 struct _FmsPart_private *part = comp->parts + part_id;
1590 const FmsInt num_entities = part->num_entities[type];
1591 void *entities_ids = part->entities_ids[type];
1592 if (num_entities != 0) {
1593 if (entities_ids == NULL) {
E_RETURN(7); }
1595 if (part->entities_ids_type[type] != id_store_type) {
E_RETURN(9); }
1596 }
else if (ents == NULL) {
1597 if (num_ents != part->domain->num_entities[type]) {
E_RETURN(10); }
1600 if (num_ents != 0) {
1601 const FmsInt nc = NextPow2(num_entities + num_ents);
1603 if (num_entities <= nc/2) {
1604 entities_ids = realloc(entities_ids, nc*sizeof_ent_ids);
1605 if (entities_ids == NULL) {
E_RETURN(11); }
1606 part->entities_ids[type] = entities_ids;
1608 FmsIntConvertCopy(ent_id_type, ents, id_store_type,
1609 (
char*)entities_ids + num_entities*sizeof_ent_ids,
1616 part->num_entities[type] = num_entities + num_ents;
1617 if (num_entities == 0) {
1618 part->entities_ids_type[type] = id_store_type;
1626 FmsInt num_relations = comp->num_relations;
1627 FmsInt *relations = comp->relations;
1628 FmsInt nc = NextPow2(num_relations + 1);
1629 if (num_relations <= nc/2) {
1630 relations = realloc(relations, nc*
sizeof(
FmsInt));
1631 if (relations == NULL) {
E_RETURN(2); }
1632 comp->relations = relations;
1634 relations[num_relations] = other_comp_id;
1635 comp->num_relations = num_relations + 1;
1641 if (coords->fd->component != comp) {
E_RETURN(2); }
1642 comp->coordinates = coords;
1659 const void *ent_tags,
FmsInt num_ents) {
1668 if (comp->num_main_entities != num_ents) {
E_RETURN(6); }
1669 if (num_ents != 0 && ent_tags == NULL) {
E_RETURN(7); }
1672 if (num_ents != 0) {
1674 if (tag->tags == NULL) {
E_RETURN(8); }
1675 FmsIntConvertCopy(input_tag_type, ent_tags, stored_tag_type, tag->tags,
1678 tag->tag_type = stored_tag_type;
1689 if (ent_tags == NULL) {
E_RETURN(4); }
1694 FmsInt num_entities = comp->num_main_entities;
1695 if (num_entities != 0) {
1696 tag->tags = malloc(num_entities*
FmsIntTypeSize[stored_tag_type]);
1697 if (tag->tags == NULL) {
E_RETURN(6); }
1699 tag->tag_type = stored_tag_type;
1700 *ent_tags = tag->tags;
1701 if (num_ents != NULL) { *num_ents = num_entities; }
1706 const char *
const *tag_descr,
FmsInt num_tags) {
1710 if (num_tags == 0) {
return 0; }
1712 if (tag_descr == NULL) {
E_RETURN(5); }
1713 const FmsInt num_tag_descriptions = tag->num_tag_descriptions;
1714 char *described_tags = tag->described_tags;
1715 char **tag_descriptions = tag->tag_descriptions;
1717 const FmsInt nc = NextPow2(num_tag_descriptions + num_tags);
1718 if (num_tag_descriptions <= nc/2) {
1719 described_tags = realloc(described_tags, nc*sizeof_tag_type);
1720 if (described_tags == NULL) {
E_RETURN(6); }
1721 tag->described_tags = described_tags;
1722 tag_descriptions = realloc(tag_descriptions, nc*
sizeof(
char*));
1723 if (tag_descriptions == NULL) {
E_RETURN(6); }
1724 tag->tag_descriptions = tag_descriptions;
1727 FmsIntConvertCopy(tag_type, tags, tag->tag_type,
1728 described_tags + num_tag_descriptions*sizeof_tag_type,
1731 for (
FmsInt i = 0; i < num_tags; i++) {
1732 if (FmsCopyString(tag_descr[i],
1733 &tag_descriptions[num_tag_descriptions + i])) {
1735 free(tag_descriptions[num_tag_descriptions + (--i)]);
1741 tag->num_tag_descriptions = num_tag_descriptions + num_tags;
1755 dcoll = calloc(1,
sizeof(*dcoll));
1756 if (dcoll == NULL) {
E_RETURN(3); }
1759 if (FmsCopyString(dc_name, &dcoll->name)) { free(dcoll);
E_RETURN(3); }
1769 if (dcoll != NULL) {
1771 FmsInt num_fields = dcoll->num_fields;
1773 for (
FmsInt i = 0; i < num_fields; i++) {
1783 FmsInt num_fds = dcoll->num_fds;
1785 for (
FmsInt i = 0; i < num_fds; i++) {
1787 switch (fd->descr_type) {
1789 default: err = UpdateError(err, 2);
1809 const char *fd_name,
1813 const FmsInt num_fds = dc->num_fds;
1816 const FmsInt nc = NextPow2(num_fds + 1);
1817 if (num_fds <= nc/2) {
1818 fds = realloc(fds, nc*
sizeof(*fds));
1823 new_fd = calloc(1,
sizeof(*new_fd));
1824 if (new_fd == NULL) {
E_RETURN(3); }
1826 if (FmsCopyString(fd_name, &new_fd->name)) { free(new_fd);
E_RETURN(3); }
1828 dc->num_fds = num_fds + 1;
1829 dc->fds[num_fds] = new_fd;
1838 const FmsInt num_fields = dc->num_fields;
1841 const FmsInt nc = NextPow2(num_fields + 1);
1842 if (num_fields <= nc/2) {
1843 fields = realloc(fields, nc*
sizeof(*fields));
1844 if (fields == NULL) {
E_RETURN(3); }
1845 dc->fields = fields;
1848 new_field = calloc(1,
sizeof(*new_field));
1849 if (new_field == NULL) {
E_RETURN(3); }
1851 if (FmsCopyString(field_name, &new_field->name)) {
1855 dc->num_fields = num_fields + 1;
1856 dc->fields[num_fields] = new_field;
1866 md = calloc(1,
sizeof(*md));
1884 fd->component = comp;
1894 if (fd->descriptor.any != NULL) {
E_RETURN(3); }
1898 const FmsInt dim = comp->dim;
1900 switch (field_type) {
1902 const FmsInt pm1 = p-1, pm2 = p-2, pm3 = p-3;
1916 const FmsInt pp1 = p+1, pp2 = p+2, pp3 = p+3;
1934 FmsAbortNotImplemented();
1938 const FmsInt pp1 = p + 1, pp2 = p + 2;
1960 for (
FmsInt i = 0; i < comp->num_parts; i++) {
1962 num_dofs += comp->parts[i].num_entities[et] * ent_dofs[et];
1967 struct _FmsFieldDescriptor_FixedOrder *fo;
1968 fo = malloc(
sizeof(*fo));
1970 fo->field_type = field_type;
1971 fo->basis_type = basis_type;
1975 fd->descriptor.fixed_order = fo;
1976 fd->num_dofs = num_dofs;
1989 if (field->fd != NULL) {
E_RETURN(2); }
1991 if (!fd->descriptor.any) {
E_RETURN(4); }
1997 const FmsInt num_vdofs = fd->num_dofs * num_vec_comp;
2000 if (num_vdofs != 0) {
2001 data_copy = malloc(num_vdofs*sizeof_data_type);
2002 if (data_copy == NULL) {
E_RETURN(8); }
2003 memcpy(data_copy, data, num_vdofs*sizeof_data_type);
2009 field->num_vec_comp = num_vec_comp;
2010 field->layout = layout_type;
2011 field->scalar_type = data_type;
2012 field->data = data_copy;
2021 md = calloc(1,
sizeof(*md));
2041 if (size && !data) {
E_RETURN(3); }
2045 void *md_data = size ? malloc(size*sizeof_int_type) : NULL;
2046 if (size && md_data == NULL) {
E_RETURN(4); }
2049 if (FmsCopyString(mdata_name, &mdata->name)) { free(md_data);
E_RETURN(4); }
2051 mdata->sub_type.int_type = int_type;
2052 mdata->num_entries = size;
2053 mdata->data = md_data;
2062 if (size && !data) {
E_RETURN(3); }
2066 void *md_data = size ? malloc(size*sizeof_scal_type) : NULL;
2067 if (size && md_data == NULL) {
E_RETURN(4); }
2070 if (FmsCopyString(mdata_name, &mdata->name)) { free(md_data);
E_RETURN(4); }
2072 mdata->sub_type.scalar_type = scal_type;
2073 mdata->num_entries = size;
2074 mdata->data = md_data;
2080 const char *c_string) {
2085 if (FmsCopyString(c_string, &md_data)) {
E_RETURN(2); }
2088 if (FmsCopyString(mdata_name, &mdata->name)) { free(md_data);
E_RETURN(2); }
2090 mdata->num_entries = md_data ? strlen(md_data) : 0;
2091 mdata->data = md_data;
2101 if (FmsCopyString(mdata_name, &name_copy)) {
E_RETURN(2); }
2103 FmsMetaData *md_data = size ? malloc(size*
sizeof(*md_data)) : NULL;
2104 if (size && md_data == NULL) { free(name_copy);
E_RETURN(2); }
2106 for (
FmsInt i = 0; i < size; i++) {
2108 md = calloc(1,
sizeof(*md));
2110 while (i != 0) { free(md_data[--i]); }
2118 mdata->name = name_copy;
2120 mdata->num_entries = size;
2121 mdata->data = md_data;
2130 switch (mdata->md_type) {
2136 for (
FmsInt i = mdata->num_entries; i != 0; ) {
2141 default: err = UpdateError(err, 2);
2148 mdata->num_entries = 0;
2170 FmsInt *num_partitions) {
2172 if (partition_id) { *partition_id = mesh->partition_id; }
2173 if (num_partitions) { *num_partitions = mesh->num_partitions; }
2179 if (!num_domain_names) {
E_RETURN(2); }
2180 *num_domain_names = mesh->num_domain_names;
2185 const char **domain_name,
FmsInt *num_domains,
2188 if (domain_name_id >= mesh->num_domain_names) {
E_RETURN(2); }
2189 if (domain_name) { *domain_name = mesh->domain_names[domain_name_id]; }
2191 *num_domains = mesh->domain_offsets[domain_name_id+1] -
2192 mesh->domain_offsets[domain_name_id];
2195 *domains = mesh->domains + mesh->domain_offsets[domain_name_id];
2204 const FmsInt num_domain_names = mesh->num_domain_names;
2205 char **domain_names = mesh->domain_names;
2206 FmsInt domain_name_id = 0;
2207 for ( ; 1; domain_name_id++) {
2208 if (domain_name_id == num_domain_names) {
E_RETURN(4); }
2209 if (strcmp(domain_name, domain_names[domain_name_id]) == 0) {
break; }
2212 *num_domains = mesh->domain_offsets[domain_name_id+1] -
2213 mesh->domain_offsets[domain_name_id];
2216 *domains = mesh->domains + mesh->domain_offsets[domain_name_id];
2224 *num_comp = mesh->num_comps;
2230 if (comp_id >= mesh->num_comps) {
E_RETURN(2); }
2232 *comp = mesh->comps[comp_id];
2239 *num_tags = mesh->num_tags;
2245 if (tag_id >= mesh->num_tags) {
E_RETURN(2); }
2247 *tag = mesh->tags[tag_id];
2259 if (domain_name) { *domain_name = domain->name; }
2260 if (domain_id) { *domain_id = domain->id; }
2274 *num_verts = domain->num_entities[
FMS_VERTEX];
2283 *num_ents = domain->num_entities[type];
2292 if (ent_id_type) { *ent_id_type = domain->side_ids_type[type]; }
2293 if (ents) { *ents = domain->entities[type]; }
2294 if (num_ents) { *num_ents = domain->num_entities[type]; }
2304 if (num_ents == 0) {
return 0; }
2305 if (first_ent >= domain->num_entities[type]) {
E_RETURN(4); }
2307 if (first_ent + num_ents > domain->num_entities[type]) {
E_RETURN(6); }
2308 void *src_ents = domain->entities[type];
2310 const FmsIntType side_ids_type = domain->side_ids_type[type];
2313 src_ents = (
char*)src_ents + first_ent*num_sides*sizeof_side_ids;
2314 if (reordering == NULL || reordering[type] == NULL) {
2315 FmsIntConvertCopy(side_ids_type, src_ents, ent_id_type, ents,
2316 num_ents*num_sides);
2318 const int *perm = reordering[type];
2319 int inv_perm[num_sides];
2320 for (
FmsInt i = 0; i < num_sides; i++) {
2321 inv_perm[perm[i]] = i;
2323 FmsIntPermuteConvertCopy(side_ids_type, src_ents, ent_id_type, ents,
2324 inv_perm, num_sides, num_ents*num_sides);
2332 void *ents_verts,
FmsInt num_ents) {
2336 if (num_ents == 0) {
return 0; }
2337 if (first_ent >= domain->num_entities[type]) {
E_RETURN(4); }
2339 if (first_ent + num_ents > domain->num_entities[type]) {
E_RETURN(6); }
2340 const char *src_ents = domain->entities[type];
2343 if (idx_type != domain->side_ids_type[type]) {
E_RETURN(8); }
2346 const int *perm = vert_reordering ? vert_reordering[type] : NULL;
2350 src_ents += first_ent*num_sides*sizeof_idx_type;
2351 if (type !=
FMS_EDGE) { side_ori += first_ent*num_sides; }
2355 FmsIntConvertCopy(idx_type, src_ents, ent_id_type, ents_verts,
2356 num_ents*num_verts);
2359 for (
FmsInt i = 0; i < 2; i++) { inv_perm[perm[i]] = i; }
2360 FmsIntPermuteConvertCopy(idx_type, src_ents, ent_id_type, ents_verts,
2361 inv_perm, num_verts, num_ents*num_verts);
2365 const void *all_edges = domain->entities[
FMS_EDGE];
2368 for (
FmsInt i = 0; i < 3; i++) { inv_perm[perm[i]] = i; }
2370 const int bsize = 1024;
2371 FmsInt tri_vert[4*bsize];
2372 FmsInt tri_vert_x[3*bsize];
2373 for (
FmsInt off = 0; off < num_ents; off += bsize) {
2374 const FmsInt sz = FmsIntMin(bsize, num_ents-off);
2376 FmsEntitiesToSides(idx_type, num_sides, 0, 2, src_ents, 2,
2377 all_edges, 4, 0, tri_vert, sz);
2379 for (
FmsInt i = 0; i < sz; i++) {
2380 const FmsInt *tv = tri_vert+4*i;
2382 FmsInt *verts = tri_vert_x+3*i;
2390 verts[2] = (eo[1] == 0) ? tv[3] : tv[2];
2394 FmsIntConvertCopy(
FMS_INT_TYPE, tri_vert_x, ent_id_type, ents_verts,
2397 FmsIntPermuteConvertCopy(
FMS_INT_TYPE, tri_vert_x, ent_id_type,
2398 ents_verts, inv_perm, num_verts, sz*num_sides);
2400 src_ents += sz*num_sides*sizeof_idx_type;
2401 side_ori += sz*num_sides;
2402 ents_verts = (
char*)ents_verts + sz*num_verts*
FmsIntTypeSize[ent_id_type];
2407 const void *all_edges = domain->entities[
FMS_EDGE];
2410 for (
FmsInt i = 0; i < 4; i++) { inv_perm[perm[i]] = i; }
2412 const int bsize = 1024;
2413 FmsInt quad_vert[4*bsize];
2414 FmsInt quad_vert_x[4*bsize];
2415 for (
FmsInt off = 0; off < num_ents; off += bsize) {
2416 const FmsInt sz = FmsIntMin(bsize, num_ents-off);
2418 FmsEntitiesToSides(idx_type, num_sides, 0, 1, src_ents, 2,
2419 all_edges, 4, 0, quad_vert, sz);
2420 FmsEntitiesToSides(idx_type, num_sides, 2, 1, src_ents, 2,
2421 all_edges, 4, 2, quad_vert, sz);
2423 for (
FmsInt i = 0; i < sz; i++) {
2424 const FmsInt *qv = quad_vert+4*i;
2426 FmsInt *verts = quad_vert_x+4*i;
2444 FmsIntConvertCopy(
FMS_INT_TYPE, quad_vert_x, ent_id_type, ents_verts,
2447 FmsIntPermuteConvertCopy(
FMS_INT_TYPE, quad_vert_x, ent_id_type,
2448 ents_verts, inv_perm, num_verts, sz*num_sides);
2450 src_ents += sz*num_sides*sizeof_idx_type;
2451 side_ori += sz*num_sides;
2452 ents_verts = (
char*)ents_verts + sz*num_verts*
FmsIntTypeSize[ent_id_type];
2458 const void *all_edges = domain->entities[
FMS_EDGE];
2461 if (!tri_side_ori) {
E_RETURN(11); }
2464 for (
FmsInt i = 0; i < 4; i++) { inv_perm[perm[i]] = i; }
2466 const int bsize = 1024;
2467 FmsInt tet_face[4*bsize];
2468 FmsInt tet_edge[6*bsize];
2469 FmsInt tet_vert_x[4*bsize];
2470 for (
FmsInt off = 0; off < num_ents; off += bsize) {
2471 const FmsInt sz = FmsIntMin(bsize, num_ents-off);
2473 FmsIntConvertCopy(idx_type, src_ents,
FMS_INT_TYPE, tet_face, sz*4);
2475 FmsEntitiesToSides(idx_type, num_sides, 1, 2, src_ents, 3,
2476 all_tris, 6, 0, tet_edge, sz);
2478 for (
FmsInt i = 0; i < sz; i++) {
2479 const FmsInt *tf = tet_face+4*i;
2480 const FmsInt *te = tet_edge+6*i;
2484 for (
int j = 0; j < 2; j++) {
2485 for (
int e = 0; e < 3; e++) {
2486 eo[3*j+e] = tri_side_ori[3*tf[j+1]+e];
2493 FmsPermuteTriBdr(so[1], te+0, te_x+0);
2494 FmsPermuteTriBdr(so[1], eo+0, eo_x+0);
2495 if (so[1]%2) {
for (
int j = 0; j < 3; j++) { eo_x[j] = 1-eo_x[j]; } }
2496 FmsPermuteTriBdr(so[2], te+3, te_x+3);
2497 FmsPermuteTriBdr(so[2], eo+3, eo_x+3);
2498 if (so[2]%2) {
for (
int j = 3; j < 6; j++) { eo_x[j] = 1-eo_x[j]; } }
2500 if (te_x[2] != te_x[4]) { FmsInternalError(); }
2501 if (eo_x[2] != 1-eo_x[4]) { FmsInternalError(); }
2503 tet_edge[2*i+0] = te_x[0];
2504 tet_edge[2*i+1] = te_x[5];
2505 tet_face[2*i+0] = eo_x[0];
2506 tet_face[2*i+1] = eo_x[5];
2510 idx_type, &tet_edge[2*bsize], 2*sz);
2511 FmsEntitiesToSides(idx_type, 2*sz, 0, 2*sz, &tet_edge[2*bsize],
2512 2, all_edges, 4*sz, 0, tet_vert_x, 1);
2514 for (
FmsInt i = 0; i < sz; i++) {
2515 FmsInt *tv = tet_vert_x+4*i, z;
2516 if (tet_face[2*i+0] != 0) {
2521 if (tet_face[2*i+1] == 0) {
2529 FmsIntConvertCopy(
FMS_INT_TYPE, tet_vert_x, ent_id_type, ents_verts,
2532 FmsIntPermuteConvertCopy(
FMS_INT_TYPE, tet_vert_x, ent_id_type,
2533 ents_verts, inv_perm, num_verts, sz*num_sides);
2535 src_ents += sz*num_sides*sizeof_idx_type;
2536 side_ori += sz*num_sides;
2537 ents_verts = (
char*)ents_verts + sz*num_verts*
FmsIntTypeSize[ent_id_type];
2543 const void *all_edges = domain->entities[
FMS_EDGE];
2547 if (!quad_side_ori) {
E_RETURN(11); }
2550 for (
FmsInt i = 0; i < 8; i++) { inv_perm[perm[i]] = i; }
2552 const int bsize = 1024;
2553 FmsInt hex_face[6*bsize];
2554 FmsInt hex_edge[8*bsize];
2555 FmsInt hex_vert_x[8*bsize];
2556 for (
FmsInt off = 0; off < num_ents; off += bsize) {
2557 const FmsInt sz = FmsIntMin(bsize, num_ents-off);
2559 FmsIntConvertCopy(idx_type, src_ents,
FMS_INT_TYPE, hex_face, sz*6);
2561 FmsEntitiesToSides(idx_type, num_sides, 0, 2, src_ents, 4,
2562 all_quads, 8, 0, hex_edge, sz);
2564 for (
FmsInt i = 0; i < sz; i++) {
2565 const FmsInt *hf = hex_face+6*i;
2566 const FmsInt *he = hex_edge+8*i;
2570 for (
int j = 0; j < 2; j++) {
2571 for (
int e = 0; e < 4; e++) {
2572 eo[4*j+e] = quad_side_ori[4*hf[j]+e];
2579 FmsPermuteQuadBdr(so[0], he+0, he_x+0);
2580 FmsPermuteQuadBdr(so[0], eo+0, eo_x+0);
2581 if (so[0]%2) {
for (
int j = 0; j < 4; j++) { eo_x[j] = 1-eo_x[j]; } }
2582 FmsPermuteQuadBdr(so[1], he+4, he_x+4);
2583 FmsPermuteQuadBdr(so[1], eo+4, eo_x+4);
2584 if (so[1]%2) {
for (
int j = 4; j < 8; j++) { eo_x[j] = 1-eo_x[j]; } }
2585 hex_edge[4*i+0] = he_x[0];
2586 hex_edge[4*i+1] = he_x[2];
2587 hex_edge[4*i+2] = he_x[4];
2588 hex_edge[4*i+3] = he_x[6];
2589 hex_face[4*i+0] = eo_x[0];
2590 hex_face[4*i+1] = eo_x[2];
2591 hex_face[4*i+2] = eo_x[4];
2592 hex_face[4*i+3] = eo_x[6];
2596 idx_type, &hex_edge[4*bsize], 4*sz);
2597 FmsEntitiesToSides(idx_type, 4*sz, 0, 4*sz, &hex_edge[4*bsize],
2598 2, all_edges, 8*sz, 0, hex_vert_x, 1);
2600 for (
FmsInt i = 0; i < sz; i++) {
2601 FmsInt *hv = hex_vert_x+8*i, z;
2602 if (hex_face[4*i+0] == 0) {
2607 if (hex_face[4*i+1] == 0) {
2612 if (hex_face[4*i+2] != 0) {
2617 if (hex_face[4*i+3] != 0) {
2625 FmsIntConvertCopy(
FMS_INT_TYPE, hex_vert_x, ent_id_type, ents_verts,
2628 FmsIntPermuteConvertCopy(
FMS_INT_TYPE, hex_vert_x, ent_id_type,
2629 ents_verts, inv_perm, num_verts, sz*num_sides);
2631 src_ents += sz*num_sides*sizeof_idx_type;
2632 side_ori += sz*num_sides;
2633 ents_verts = (
char*)ents_verts + sz*num_verts*
FmsIntTypeSize[ent_id_type];
2639 default: FmsAbortNotImplemented();
2649 if (side_orients) { *side_orients = domain->orientations[type]; }
2650 if (num_ents) { *num_ents = domain->num_entities[type]; }
2661 if (comp_name) { *comp_name = comp->name; }
2667 if (dim) { *dim = comp->dim; }
2673 if (num_parts) { *num_parts = comp->num_parts; }
2682 if (part_id >= comp->num_parts) {
E_RETURN(2); }
2685 struct _FmsPart_private *part = &comp->parts[part_id];
2686 if (domain) { *domain = part->domain; }
2687 if (ent_id_type) { *ent_id_type = part->entities_ids_type[type]; }
2688 if (ents) { *ents = part->entities_ids[type]; }
2689 if (ent_orients) { *ent_orients = part->orientations[type]; }
2690 if (num_ents) { *num_ents = part->num_entities[type]; }
2696 const void **ents,
FmsInt *num_ents) {
2698 if (part_id >= comp->num_parts) {
E_RETURN(2); }
2701 struct _FmsPart_private *part = &comp->parts[part_id];
2702 if (ent_id_type) { *ent_id_type = part->entities_ids_type[type]; }
2703 if (ents) { *ents = part->entities_ids[type]; }
2704 if (num_ents) { *num_ents = part->num_entities[type]; }
2710 if (num_ents) { *num_ents = comp->num_main_entities; }
2717 if (rel_comps) { *rel_comps = comp->relations; }
2718 if (num_rel_comps) { *num_rel_comps = comp->num_relations; }
2724 if (coords) { *coords = comp->coordinates; }
2735 if (tag_name) { *tag_name = tag->name; }
2741 if (comp) { *comp = tag->comp; }
2748 if (tag_type) { *tag_type = tag->tag_type; }
2749 if (ent_tags) { *ent_tags = tag->tags; }
2750 if (num_ents) { *num_ents = tag->comp->num_main_entities; }
2755 const char *
const **tag_descr,
FmsInt *num_tags) {
2757 if (tag_type) { *tag_type = tag->tag_type; }
2758 if (tags) { *tags = tag->described_tags; }
2761 *tag_descr = (
const char *
const *)(tag->tag_descriptions);
2763 if (num_tags) { *num_tags = tag->num_tag_descriptions; }
2789 if (fds) { *fds = dc->fds; }
2790 if (num_fds) { *num_fds = dc->num_fds; }
2797 if (fields) { *fields = dc->fields; }
2798 if (num_fields) { *num_fields = dc->num_fields; }
2817 *fd_name = fd->name;
2824 *comp = fd->component;
2832 *fd_type = fd->descr_type;
2840 struct _FmsFieldDescriptor_FixedOrder *fo = fd->descriptor.fixed_order;
2841 if (field_type) { *field_type = fo->field_type; }
2842 if (basis_type) { *basis_type = fo->basis_type; }
2843 if (order) { *order = fo->order; }
2850 *num_dofs = fd->num_dofs;
2862 *field_name = field->name;
2868 const void **data) {
2870 if (fd) { *fd = field->fd; }
2871 if (num_vec_comp) { *num_vec_comp = field->num_vec_comp; }
2872 if (layout_type) { *layout_type = field->layout; }
2873 if (data_type) { *data_type = field->scalar_type; }
2874 if (data) { *data = field->data; }
2881 *mdata = field->mdata;
2893 *type = mdata->md_type;
2899 const void **data) {
2901 if (mdata_name) { *mdata_name = mdata->name; }
2902 if (int_type) { *int_type = mdata->sub_type.int_type; }
2903 if (size) { *size = mdata->num_entries; }
2904 if (data) { *data = mdata->data; }
2910 const void **data) {
2912 if (mdata_name) { *mdata_name = mdata->name; }
2913 if (scal_type) { *scal_type = mdata->sub_type.scalar_type; }
2914 if (size) { *size = mdata->num_entries; }
2915 if (data) { *data = mdata->data; }
2920 const char **c_string) {
2922 if (mdata_name) { *mdata_name = mdata->name; }
2923 if (c_string) { *c_string = mdata->data; }
2930 if (mdata_name) { *mdata_name = mdata->name; }
2931 if (size) { *size = mdata->num_entries; }
2932 if (data) { *data = mdata->data; }
2939 static inline double FmsAbs(
const double x) {
2940 if(x < 0.)
return -x;
2945 #define COMPARE_SCALAR_DATA(T, lhs, rhs, n, OUT_FmsInt_isdifferent) \ 2947 const T *lhs_data = (const T*)lhs; \ 2948 const T *rhs_data = (const T*)rhs; \ 2949 const FmsInt N = n; \ 2950 OUT_FmsInt_isdifferent = 0; \ 2951 for(FmsInt i = 0; i < N; i++) { \ 2952 if(FmsAbs(lhs_data[i] - rhs_data[i]) > 1e-6) { \ 2953 OUT_FmsInt_isdifferent = i+1; \ 2959 #define COMPARE_INT_DATA(T, lhs, rhs, n, OUT_FmsInt_isdifferent) \ 2961 const T *lhs_data = (const T*)lhs; \ 2962 const T *rhs_data = (const T*)rhs; \ 2963 const FmsInt N = n; \ 2964 OUT_FmsInt_isdifferent = 0; \ 2965 for(FmsInt i = 0; i < N; i++) { \ 2966 if(lhs_data[i] != rhs_data[i]) { \ 2967 OUT_FmsInt_isdifferent = i+1; \ 2974 const void *lhs,
const void *rhs) {
2975 if(lhs == rhs)
return 0;
2999 const void *lhs,
const void *rhs) {
3000 if(lhs == rhs)
return 0;
3036 if(lhs == rhs)
return 0;
3041 const char *lhs_name = NULL;
3042 const char *rhs_name = NULL;
3045 if(strcmp(lhs_name, rhs_name)) {
3050 FmsMesh lhs_mesh = NULL, rhs_mesh = NULL;
3059 FmsInt lhs_nfds = 0, rhs_nfds = -1;
3062 if(lhs_nfds != rhs_nfds) {
3065 for(
FmsInt i = 0; i < lhs_nfds; i++) {
3073 FmsField *lhs_fields = NULL, *rhs_fields = NULL;
3074 FmsInt lhs_nfields = 0, rhs_nfields = -1;
3077 if(lhs_nfds != rhs_nfds) {
3080 for(
FmsInt i = 0; i < lhs_nfds; i++) {
3098 if(lhs == rhs)
return 0;
3103 FmsInt lhs_ndnames = 0, rhs_ndnames = -1;
3108 if(lhs_ndnames != rhs_ndnames) {
3111 for(
FmsInt i = 0; i < lhs_ndnames; i++) {
3112 const char *lhs_dname = NULL, *rhs_dname = NULL;
3113 FmsInt lhs_ndomains = 0, rhs_ndomains = -1;
3114 FmsDomain *lhs_domains = NULL, *rhs_domains = NULL;
3117 if(strcmp(lhs_dname, rhs_dname)) {
3121 if(lhs_ndomains != rhs_ndomains) {
3125 for(
FmsInt j = 0; j < lhs_ndnames; j++) {
3134 FmsInt lhs_ncomponents = 0, rhs_ncomponents = -1;
3137 if(lhs_ncomponents != rhs_ncomponents) {
3140 for(
FmsInt i = 0; i < lhs_ncomponents; i++) {
3141 FmsComponent lhs_component = NULL, rhs_component = NULL;
3151 FmsInt lhs_ntags = 0, rhs_ntags = -1;
3154 if(lhs_ntags != rhs_ntags) {
3157 for(
FmsInt i = 0; i < lhs_ntags; i++) {
3158 FmsTag lhs_tag = NULL, rhs_tag = NULL;
3175 if(lhs == rhs)
return 0;
3180 if(strcmp(lhs->name, rhs->name)) {
3184 if(lhs->descr_type != rhs->descr_type) {
3189 if(lhs->descriptor.fixed_order && rhs->descriptor.fixed_order) {
3190 if(lhs->descriptor.fixed_order->basis_type !=
3191 rhs->descriptor.fixed_order->basis_type) {
3194 if(lhs->descriptor.fixed_order->field_type !=
3195 rhs->descriptor.fixed_order->field_type) {
3198 if(lhs->descriptor.fixed_order->order != rhs->descriptor.fixed_order->order) {
3201 }
else if(!lhs->descriptor.fixed_order) {
3203 }
else if(!rhs->descriptor.fixed_order) {
3211 if(lhs->num_dofs != rhs->num_dofs) {
3218 if(lhs->component && rhs->component) {
3219 if(lhs->component->name && rhs->component->name) {
3220 if(strcmp(lhs->component->name, rhs->component->name)) {
3223 }
else if(!lhs->component->name)
3225 else if(!rhs->component->name)
3227 }
else if(!lhs->component)
3229 else if(!rhs->component)
3237 if(lhs == rhs)
return 0;
3242 if(strcmp(lhs->name, rhs->name)) {
3250 if(lhs->num_vec_comp != rhs->num_vec_comp) {
3254 if(lhs->scalar_type != rhs->scalar_type) {
3259 if(lhs->layout != rhs->layout) {
3265 FmsInt nvdim = lhs->num_vec_comp;
3268 nDofs = lhs->fd->num_dofs;
3269 if(CompareScalarData(lhs->scalar_type, nvdim * nDofs, lhs->data, rhs->data))
3277 if(lhs == rhs)
return 0;
3283 if(lhs->name && rhs->name) {
3284 if(strcmp(lhs->name, rhs->name))
3286 }
else if(!lhs->name)
3292 if(lhs->md_type != rhs->md_type) {
3298 switch(lhs->md_type) {
3300 if(lhs->sub_type.int_type != rhs->sub_type.int_type)
3303 if(lhs->num_entries != rhs->num_entries)
3307 if(CompareIntData(lhs->sub_type.int_type, lhs->num_entries, lhs->data,
3314 if(lhs->sub_type.scalar_type != rhs->sub_type.scalar_type)
3317 if(lhs->num_entries != rhs->num_entries)
3321 if(CompareScalarData(lhs->sub_type.scalar_type, lhs->num_entries, lhs->data,
3328 if(lhs->data && rhs->data) {
3329 if(strcmp(lhs->data, rhs->data))
3331 }
else if(!lhs->name)
3338 if(lhs->num_entries != rhs->num_entries)
3344 const FmsInt NE = lhs->num_entries;
3345 for(
FmsInt i = 0; i < NE; i++) {
3363 if(lhs == rhs)
return 0;
3369 if(lhs->name && rhs->name) {
3370 if(strcmp(lhs->name, rhs->name))
3372 }
else if(!lhs->name)
3378 if(lhs->id != rhs->id)
3382 if(lhs->dim != rhs->dim)
3387 if(lhs->num_entities[i] != rhs->num_entities[i]) {
3395 if(lhs->side_ids_type[i] != rhs->side_ids_type[i]) {
3404 if(CompareIntData(lhs->side_ids_type[i],
3406 lhs->entities[i], rhs->entities[i])) {
3417 lhs->orientations[i], rhs->orientations[i])) {
3428 if(lhs == rhs)
return 0;
3433 if(lhs->name && rhs->name) {
3434 if(strcmp(lhs->name, rhs->name))
3436 }
else if(!lhs->name)
3441 if(lhs->id != rhs->id)
3444 if(lhs->dim != rhs->dim)
3447 if(lhs->num_main_entities != rhs->num_main_entities)
3450 if(lhs->num_parts != rhs->num_parts)
3453 if(lhs->num_relations != rhs->num_relations)
3457 const FmsInt np = lhs->num_parts;
3458 for(
FmsInt i = 0; i < np; i++) {
3459 const struct _FmsPart_private *lpart = &lhs->parts[i];
3460 const struct _FmsPart_private *rpart = &rhs->parts[i];
3466 if(lpart->num_entities[j] != rpart->num_entities[j]) {
3470 if(lpart->entities_ids_type[j] != rpart->entities_ids_type[j]) {
3474 if(CompareIntData(lpart->entities_ids_type[j],
3475 lpart->num_entities[j],
3476 lpart->entities_ids[j], rpart->entities_ids[j])) {
3487 if(CompareIntData(
FMS_INT_TYPE, lhs->num_relations, lhs->relations,
3502 if(lhs == rhs)
return 0;
3507 if(lhs->name && rhs->name) {
3508 if(strcmp(lhs->name, rhs->name))
3510 }
else if(!lhs->name)
3515 if(lhs->tag_type != rhs->tag_type)
3518 if(lhs->num_tag_descriptions != rhs->num_tag_descriptions)
3527 FmsInt ne = lhs->comp->num_main_entities;
3528 if(CompareIntData(lhs->tag_type, ne, lhs->tags, rhs->tags))
int FmsGetInterfaceVersion(FmsInt *version)
Get the interface version.
#define FMS_ICC_SW(src_type, src, dst_t, dst, size)
int FmsComponentAddPartEntities(FmsComponent comp, FmsInt part_id, FmsEntityType type, FmsIntType id_store_type, FmsIntType ent_id_type, FmsIntType orient_type, const FmsOrientation *inv_orient_map, const void *ents, const void *ent_orients, FmsInt num_ents)
TODO: dox.
int FmsComponentGetNumParts(FmsComponent comp, FmsInt *num_parts)
TODO: dox.
int FmsGetMetaDataTypeFromName(const char *const name, FmsMetaDataType *type)
Convert a meta-data-type string to FmsMetaDataType value.
int FmsDomainGetDimension(FmsDomain domain, FmsInt *dim)
Return the highest dimension of an entry in a mesh domain.
int FmsMeshGetDomainsByName(FmsMesh mesh, const char *domain_name, FmsInt *num_domains, FmsDomain **domains)
TODO: dox.
int FmsComponentGetName(FmsComponent comp, const char **comp_name)
Return the name of a mesh component.
int FmsMeshFinalize(FmsMesh mesh)
TODO: dox.
int FmsTagSetComponent(FmsTag tag, FmsComponent comp)
TODO: dox.
int FmsTagGetName(FmsTag tag, const char **tag_name)
TODO: dox.
int FmsDataCollectionGetMetaData(FmsDataCollection dc, FmsMetaData *mdata)
TODO: dox.
int FmsComponentAddPartSubEntities(FmsComponent comp, FmsInt part_id, FmsEntityType type, FmsIntType id_store_type, FmsIntType ent_id_type, const void *ents, FmsInt num_ents)
TODO: dox Similar to FmsComponentAddPartEntities() but for lower dimensional entities.
int FmsDomainAddEntities(FmsDomain domain, FmsEntityType type, FmsEntityReordering reordering, FmsIntType ent_id_type, const void *ents, FmsInt num_ents)
TODO: dox.
int FmsTagGetComponent(FmsTag tag, FmsComponent *comp)
TODO: dox.
int FmsMeshGetNumTags(FmsMesh mesh, FmsInt *num_tags)
TODO: dox.
int FmsMeshGetComponent(FmsMesh mesh, FmsInt comp_id, FmsComponent *comp)
TODO: dox.
const int * FmsEntityReordering[FMS_NUM_ENTITY_TYPES]
A type describing user-defined local orderings of the side entities defining an enitity.
int FmsMeshGetNumDomainNames(FmsMesh mesh, FmsInt *num_domain_names)
TODO: dox.
const char *const FmsEntityTypeNames[FMS_NUM_ENTITY_TYPES]
String representations of each entity type.
int FmsFieldCompare(FmsField lhs, FmsField rhs)
Return 0 if equivalent, not 0 otherwise.
int FmsComponentAddRelation(FmsComponent comp, FmsInt other_comp_id)
Describe a relation from one component to another.
int FmsDomainGetEntitiesArray(FmsDomain domain, FmsEntityType type, void **ents)
TODO: dox.
FmsMetaDataType
TODO: dox.
int FmsDataCollectionGetFieldDescriptors(FmsDataCollection dc, FmsFieldDescriptor **fds, FmsInt *num_fds)
TODO: dox.
struct FmsFieldDescriptor_private * FmsFieldDescriptor
TODO: dox.
int FmsComponentCompare(FmsComponent lhs, FmsComponent rhs)
Return 0 if equivalent, not 0 otherwise.
int FmsTagGetDescriptions(FmsTag tag, FmsIntType *tag_type, const void **tags, const char *const **tag_descr, FmsInt *num_tags)
TODO: dox.
int FmsDomainGetEntitiesVerts(FmsDomain domain, FmsEntityType type, FmsEntityReordering vert_reordering, FmsIntType ent_id_type, FmsInt first_ent, void *ents_verts, FmsInt num_ents)
TODO: dox Extract a subset of the entity definitions in terms of their vertices.
int FmsMeshValidate(FmsMesh mesh)
TODO: dox.
int FmsComponentAddPart(FmsComponent comp, FmsDomain domain, FmsInt *part_id)
TODO: dox.
const char *const FmsMetaDataTypeNames[FMS_NUM_METADATA_TYPES]
Added in version: v0.2.
The type of FmsInt identified as FmsIntType.
struct FmsComponent_private * FmsComponent
TODO: dox.
int FmsMetaDataGetIntegers(FmsMetaData mdata, const char **mdata_name, FmsIntType *int_type, FmsInt *size, const void **data)
Get the contents of a meta-data structure that stores an array of integers.
int FmsMetaDataGetScalars(FmsMetaData mdata, const char **mdata_name, FmsScalarType *scal_type, FmsInt *size, const void **data)
Get the contents of a meta-data structure that stores an array of scalars.
int FmsDomainGetAllOrientations(FmsDomain domain, FmsEntityType type, const FmsOrientation **side_orients, FmsInt *num_ents)
TODO: dox No copy, read only access to all entity side orientations.
int FmsDomainGetEntities(FmsDomain domain, FmsEntityType type, FmsEntityReordering reordering, FmsIntType ent_id_type, FmsInt first_ent, void *ents, FmsInt num_ents)
TODO: dox Extract a subset of the entity definitions.
int FmsMetaDataCompare(FmsMetaData lhs, FmsMetaData rhs)
Return 0 if equivalent, not 0 otherwise.
int FmsFieldDescriptorGetComponent(FmsFieldDescriptor fd, FmsComponent *comp)
TODO: dox.
const FmsInt FmsEntityNumVerts[FMS_NUM_ENTITY_TYPES]
Number of vertices of the entity types.
int FmsMetaDataDestroy(FmsMetaData *mdata)
Destroy the object that *mdata refers to and set *mdata to NULL.
int FmsTagSet(FmsTag tag, FmsIntType stored_tag_type, FmsIntType input_tag_type, const void *ent_tags, FmsInt num_ents)
TODO: dox.
const char *const FmsScalarTypeNames[FMS_NUM_SCALAR_TYPES]
Added in version: v0.2.
FmsFieldDescriptorType
Field descriptor types supported by FMS, see FmsFieldDescriptor.
int FmsMeshDestroy(FmsMesh *mesh)
TODO: dox.
int FmsDataCollectionGetName(FmsDataCollection dc, const char **name)
Get the name of the data collection.
int FmsDataCollectionAddFieldDescriptor(FmsDataCollection dc, const char *fd_name, FmsFieldDescriptor *fd)
TODO: dox.
int FmsDomainGetAllEntities(FmsDomain domain, FmsEntityType type, FmsIntType *ent_id_type, const void **ents, FmsInt *num_ents)
TODO: dox No copy, read only access to all entity definitions.
int FmsFieldAttachMetaData(FmsField field, FmsMetaData *mdata)
Make sure the meta-data structure associated with a field is allocated and return it in mdata...
struct FmsDomain_private * FmsDomain
TODO: dox.
int FmsMeshConstruct(FmsMesh *mesh)
Allocate a mesh structure and initialize it to be empty.
int FmsFieldGet(FmsField field, FmsFieldDescriptor *fd, FmsInt *num_vec_comp, FmsLayoutType *layout_type, FmsScalarType *data_type, const void **data)
TODO: dox.
See FmsFieldDescriptorSetFixedOrder()
int FmsDomainSetNumVertices(FmsDomain domain, FmsInt num_verts)
Set the number of vertices in a domain.
int FmsDomainGetNumVertices(FmsDomain domain, FmsInt *num_verts)
Get the number of vertices in a domain.
int FmsFieldDescriptorGetName(FmsFieldDescriptor fd, const char **fd_name)
TODO: dox.
int FmsDataCollectionAddField(FmsDataCollection dc, const char *field_name, FmsField *field)
TODO: dox.
#define COMPARE_SCALAR_DATA(T, lhs, rhs, n, OUT_FmsInt_isdifferent)
int FmsDataCollectionAttachMetaData(FmsDataCollection dc, FmsMetaData *mdata)
Make sure the meta-data structure associated with a data collection is allocated and return it in mda...
uint64_t FmsInt
Type used by fms for representing and storing sizes and indices.
const char *const FmsIntTypeNames[FMS_NUM_INT_TYPES]
Added in version: v0.2.
int FmsComponentGetRelations(FmsComponent comp, const FmsInt **rel_comps, FmsInt *num_rel_comps)
TODO: dox.
int FmsDomainGetNumEntities(FmsDomain domain, FmsEntityType type, FmsInt *num_ents)
Get the number of entities of a given type in a domain.
int FmsMetaDataClear(FmsMetaData mdata)
Clear the contents of mdata without destroying the object.
int FmsMetaDataGetType(FmsMetaData mdata, FmsMetaDataType *type)
TODO: dox.
int FmsGetIntTypeFromName(const char *const name, FmsIntType *type)
Get the enum representation of an int type from the string name.
int FmsFieldDescriptorGetType(FmsFieldDescriptor fd, FmsFieldDescriptorType *fd_type)
TODO: dox.
int FmsTagAllocate(FmsTag tag, FmsIntType stored_tag_type, void **ent_tags, FmsInt *num_ents)
TODO: dox.
int FmsDataCollectionCompare(FmsDataCollection lhs, FmsDataCollection rhs)
Comparison interface.
int FmsTagCompare(FmsTag lhs, FmsTag rhs)
Return 0 if equivalent, not 0 otherwise.
#define COMPARE_INT_DATA(T, lhs, rhs, n, OUT_FmsInt_isdifferent)
int FmsTagAddDescriptions(FmsTag tag, FmsIntType tag_type, const void *tags, const char *const *tag_descr, FmsInt num_tags)
TODO: dox.
int FmsDataCollectionCreate(FmsMesh mesh, const char *dc_name, FmsDataCollection *dc)
TODO: dox The new object, dc, assumes ownership of the mesh.
int FmsFieldDescriptorCompare(FmsFieldDescriptor lhs, FmsFieldDescriptor rhs)
Return 0 if equivalent, not 0 otherwise.
int FmsFieldSet(FmsField field, FmsFieldDescriptor fd, FmsInt num_vec_comp, FmsLayoutType layout_type, FmsScalarType data_type, const void *data)
TODO: dox The size of the data array is num_vec_comp times the number of DOFs as defined by the field...
int FmsMeshGetTag(FmsMesh mesh, FmsInt tag_id, FmsTag *tag)
TODO: dox.
The type of FmsOrientation as FmsIntType.
int FmsMeshSetPartitionId(FmsMesh mesh, FmsInt partition_id, FmsInt num_partitions)
TODO: dox.
int FmsDomainCompare(FmsDomain lhs, FmsDomain rhs)
Return 0 if equivalent, not 0 otherwise.
int FmsDataCollectionDestroy(FmsDataCollection *dc)
Destroy a data collection object.
int FmsMetaDataSetIntegers(FmsMetaData mdata, const char *mdata_name, FmsIntType int_type, FmsInt size, void **data)
Set the contents of a meta-data structure to store an array of integers.
int FmsDomainGetOrientationsArray(FmsDomain domain, FmsEntityType type, FmsOrientation **side_orients)
TODO: dox.
#define FMS_E2S_TEMPL(idx_t)
int FmsMetaDataGetString(FmsMetaData mdata, const char **mdata_name, const char **c_string)
Get the contents of a meta-data structure that stores a c-string.
int FmsMeshGetNumComponents(FmsMesh mesh, FmsInt *num_comp)
TODO: dox.
int FmsMeshGetPartitionId(FmsMesh mesh, FmsInt *partition_id, FmsInt *num_partitions)
TODO: dox.
struct FmsTag_private * FmsTag
TODO: dox.
int FmsComponentSetCoordinates(FmsComponent comp, FmsField coords)
Set the coordinates field of a component.
int FmsFieldDescriptorSetFixedOrder(FmsFieldDescriptor fd, FmsFieldType field_type, FmsBasisType basis_type, FmsInt order)
TODO: dox.
struct FmsField_private * FmsField
Discrete field data type.
int FmsMeshAddTag(FmsMesh mesh, const char *tag_name, FmsTag *tag)
Add a new tag to the mesh with the given name and return the new tag in tag.
int FmsFieldDescriptorGetNumDofs(FmsFieldDescriptor fd, FmsInt *num_dofs)
TODO: dox.
int FmsMetaDataSetString(FmsMetaData mdata, const char *mdata_name, const char *c_string)
Set the contents of a meta-data structure to store a c-string.
int FmsDomainSetNumEntities(FmsDomain domain, FmsEntityType type, FmsIntType id_store_type, FmsInt num_ents)
Allocates memory for the specified entities.
int FmsDomainAddOrientation(FmsDomain domain, FmsEntityType type, FmsInt ent_id, FmsInt loc_side_id, FmsOrientation side_orient)
TODO: dox.
FmsScalarType
Scalar types supported by FMS: floating-point types, real and complex.
int FmsMetaDataGetMetaData(FmsMetaData mdata, const char **mdata_name, FmsInt *size, FmsMetaData **data)
Get the contents of a meta-data structure that stores an array of meta-data structures.
struct FmsDataCollection_private * FmsDataCollection
Data collection type: contains a mesh, discrete fileds, meta-data, etc.
int FmsTagGet(FmsTag tag, FmsIntType *tag_type, const void **ent_tags, FmsInt *num_ents)
TODO: dox No copy, read only access to the entity-tag array.
int FmsFieldDescriptorSetComponent(FmsFieldDescriptor fd, FmsComponent comp)
TODO: dox.
int FmsDataCollectionGetMesh(FmsDataCollection dc, FmsMesh *mesh)
TODO: dox.
const FmsInt FmsEntityNumSides[FMS_NUM_ENTITY_TYPES]
Number of sides of the entity types.
int FmsMeshAddDomains(FmsMesh mesh, const char *domain_name, FmsInt num_domains, FmsDomain **domains)
Allocates an array of domains sharing the same name, initializes them, and returns a pointer to the a...
struct FmsMesh_private * FmsMesh
TODO: dox.
int FmsDomainGetName(FmsDomain domain, const char **domain_name, FmsInt *domain_id)
Return the name and id of a mesh domain.
int FmsMeshAddComponent(FmsMesh mesh, const char *comp_name, FmsComponent *comp)
Add a new empty component to the mesh with the given name and return the new component in comp...
int FmsComponentGetCoordinates(FmsComponent comp, FmsField *coords)
Return the coordinates field of a component.
int FmsComponentGetPart(FmsComponent comp, FmsInt part_id, FmsEntityType type, FmsDomain *domain, FmsIntType *ent_id_type, const void **ents, const FmsOrientation **ent_orients, FmsInt *num_ents)
TODO: dox.
int FmsFieldGetName(FmsField field, const char **field_name)
TODO: dox.
int FmsGetScalarTypeFromName(const char *const name, FmsScalarType *type)
Get the enum representation of an int type from the string name.
int FmsComponentAddDomain(FmsComponent comp, FmsDomain domain)
TODO: dox.
int FmsFieldDescriptorGetFixedOrder(FmsFieldDescriptor fd, FmsFieldType *field_type, FmsBasisType *basis_type, FmsInt *order)
TODO: dox.
int FmsComponentGetPartSubEntities(FmsComponent comp, FmsInt part_id, FmsEntityType type, FmsIntType *ent_id_type, const void **ents, FmsInt *num_ents)
TODO: dox Similar to FmsComponentGetPart() but for lower dimensional entities.
struct FmsMetaData_private * FmsMetaData
TODO: dox.
#define FMS_IPCC_SW(src_type, src, dst_t, dst, ts, perm, size)
int FmsMeshGetDomains(FmsMesh mesh, FmsInt domain_name_id, const char **domain_name, FmsInt *num_domains, FmsDomain **domains)
TODO: dox.
#define FMS_IMC_SW(src_type, src, dst_t, dst, map, size)
int FmsDataCollectionGetFields(FmsDataCollection dc, FmsField **fields, FmsInt *num_fields)
TODO: dox.
int FmsMetaDataSetScalars(FmsMetaData mdata, const char *mdata_name, FmsScalarType scal_type, FmsInt size, void **data)
Set the contents of a meta-data structure to store an array of scalars.
int FmsComponentGetDimension(FmsComponent comp, FmsInt *dim)
Return the dimension of a mesh component.
int FmsGetEntityTypeFromName(const char *const name, FmsEntityType *ent_type)
Convert an entity-type string to FmsEntityType value.
int FmsMetaDataSetMetaData(FmsMetaData mdata, const char *mdata_name, FmsInt size, FmsMetaData **data)
Set the contents of a meta-data structure to store an array of meta-data structures.
const size_t FmsScalarTypeSize[FMS_NUM_SCALAR_TYPES]
int FmsMeshCompare(FmsMesh lhs, FmsMesh rhs)
Return 0 if equivalent, not 0 otherwise.
uint8_t FmsOrientation
A type used by fms to represent and store entity orientations.
const size_t FmsIntTypeSize[FMS_NUM_INT_TYPES]
int FmsComponentGetNumEntities(FmsComponent comp, FmsInt *num_ents)
Return the total number of main entities across all parts in the component.
int FmsFieldGetMetaData(FmsField field, FmsMetaData *mdata)
TODO: dox.
const FmsInt FmsEntityDim[FMS_NUM_ENTITY_TYPES]
Dimensions of the entity types.