Cloned library of VTK-5.0.0 with extra build files for internal package management.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

1006 lines
36 KiB

/*
* Copyright (c) 1994 Sandia Corporation. Under the terms of Contract
* DE-AC04-94AL85000 with Sandia Corporation, the U.S. Governement
* retains certain rights in this software.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials provided
* with the distribution.
*
* * Neither the name of Sandia Corporation nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
/*****************************************************************************
*
* excn2s - ex_cvt_nodes_to_sides: convert nodes to sides
*
* author - Sandia National Laboratories
* Vic Yarberry - Original
*
*
* environment - UNIX
*
* entry conditions -
* input parameters:
* int exoid exodus file id
* int *num_elem_per_set number of element per set
* int *num_nodes_per_set number of nodes per set
* int *side_sets_elem_index index array of elements into elem list
* int *side_sets_node_index index array of nodes
* int *side_sets_elem_list array of elements
* int *side_sets_node_list array of nodes
*
* exit conditions -
* int *side_sets_side_list array of sides/faces
*
* revision history -
*
* $Id: excn2s.c,v 1.4 2005/07/19 23:40:10 andy Exp $
*
*****************************************************************************/
#include <ctype.h>
#include <string.h>
#include <stdlib.h>
#include "exodusII.h"
#include "exodusII_int.h"
/*
* This routine is designed to take the results from retrieving the ExodusI
* style concatenated side sets to the Exodus II V 2.0 definition
* uses the element id to get the coordinate node list, element block
* connectivity, element type to
* convert the side set node list to a side/face list.
Algorithm:
Read elem_block_ids --> elem_blk_id[array]
Read element block parameters --> elem_blk_parms[array]
Determine total number of elements in side set by summing num_elem_per_set
Build side set element to side set node list index --> ss_elem_node_ndx[array]
For each element in the side_set_elem_list
{
If Jth element is not in current element block (e.g. J>elem_ctr)
{
get element block parameters (num_elem_in_blk, ...)
elem_ctr += num_elem_in_blk
free old connectity array space
allocate connectivity array: size=num_elem_in_blk*num_nodes_per_elem
get connectivity array
}
If Jth element is in current element block (e.g. J<=elem_ctr)
{
For each node in element (linear search of up to num_nodes_per_elem)
{
If side set element node[1] == element node[i]
{
Case element type = Hex
{
If side set element node[2] == element node[Hex_table[i,1]]
Jth side = Hex_table[i,2]
break
}
Case element type = Wedge
{
If side set element node[2] == element node[Wedge_table[i,1]]
Jth side = Wedge_table[i,2]
break
}
}
}
}
}
*/
int ex_cvt_nodes_to_sides(int exoid,
int *num_elem_per_set,
int *num_nodes_per_set,
int *side_sets_elem_index,
int *side_sets_node_index,
int *side_sets_elem_list,
int *side_sets_node_list,
int *side_sets_side_list)
{
int i, j, k, m, n;
int num_side_sets, num_elem_blks;
int tot_num_elem = 0, tot_num_ss_elem = 0, elem_num = 0, ndim;
int *elem_blk_ids, *connect;
int *ss_elem_ndx, *ss_elem_node_ndx, *ss_parm_ndx;
int elem_ctr, node_ctr, elem_num_pos;
int num_elem_in_blk, num_nodes_per_elem, num_node_per_side, num_attr;
int *same_elem_type, el_type;
float fdum;
char *cdum, elem_type[MAX_STR_LENGTH+1];
struct elem_blk_parm
{
char elem_type[MAX_STR_LENGTH+1];
int elem_blk_id;
int num_elem_in_blk;
int num_nodes_per_elem;
int num_nodes_per_side;
int num_attr;
int elem_ctr;
int elem_type_val;
} *elem_blk_parms;
/* node to side translation tables -
These tables are used to look up the side number based on the
first and second node in the side/face list. The side node order
is found in the original Exodus document, SAND87-2997. The element
node order is found in the ExodusII document, SAND92-2137. These
tables were generated by following the right-hand rule for determining
the outward normal. Note: Only the more complex 3-D shapes require
these tables, the simple shapes are trivial - the first node found
is also the side number.
*/
/* 1 2 3 4 node 1 */
static int shell_table[2][8] = {
{2,4, 3,1, 4,2, 1,3}, /* node 2 */
{1,2, 1,2, 1,2, 1,2} /* side # */
};
/* 1 2 3 4 node 1 */
static int shell_edge_table[2][8] = {
{2,4, 3,1, 4,2, 1,3}, /* node 2 */
{3,6, 4,3, 5,4, 6,5} /* side # */
};
/* 1 2 3 node 1 */
static int trishell_table[2][6] = {
{2,3, 3,1, 1,2}, /* node 2 */
{1,2, 1,2, 1,2} /* side # */
};
/* 1 2 3 4 node 1 */
static int tetra_table[2][12] = {
{2,3,4, 1,3,4, 4,1,2, 1,2,3}, /* node 2 */
{1,4,3, 4,2,1, 2,3,4, 1,2,3} /* side # */
};
#if 0
static int wedge_table[2][18] = {
/* 1 2 3 4 5 6 node 1 */
{2,4,3, 5,1,3, 6,1,2, 1,6,5, 6,2,4, 4,3,5}, /* node 2 */
{1,3,4, 1,4,2, 2,3,4, 1,3,5, 5,2,1, 5,3,2} /* side # */
};
#endif
static int hex_table[2][24] = {
/* 1 2 3 4 5 6 7 8 node 1 */
{4,2,5, 1,3,6, 7,4,2, 3,1,8, 6,8,1, 5,2,7, 8,6,3, 7,5,4},/* node 2 */
{5,1,4, 5,2,1, 2,3,5, 5,4,3, 6,4,1, 1,2,6, 6,2,3, 3,6,4} /* side # */
};
char errmsg[MAX_ERR_LENGTH];
(void)side_sets_node_index;
(void)side_sets_elem_index;
exerrval = 0; /* clear error code */
cdum = 0; /* initialize even though it is not used */
/* first check if any side sets are specified */
/* inquire how many side sets have been stored */
if ((ex_inquire(exoid, EX_INQ_SIDE_SETS, &num_side_sets, &fdum, cdum)) == -1)
{
sprintf(errmsg,
"Error: failed to get number of side sets in file id %d",exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return(EX_FATAL);
}
if (num_side_sets == 0)
{
sprintf(errmsg,
"Warning: no side sets defined in file id %d",exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,EX_WARN);
return(EX_WARN);
}
if ((ex_inquire(exoid, EX_INQ_ELEM_BLK, &num_elem_blks, &fdum, cdum)) == -1)
{
sprintf(errmsg,
"Error: failed to get number of element blocks in file id %d",exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return(EX_FATAL);
}
if ((ex_inquire(exoid, EX_INQ_ELEM, &tot_num_elem, &fdum, cdum)) == -1)
{
sprintf(errmsg,
"Error: failed to get total number of elements in file id %d",exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return(EX_FATAL);
}
/* get the dimensionality of the coordinates; this is necessary to
distinguish between 2d TRIs and 3d TRIs */
if ((ex_inquire(exoid, EX_INQ_DIM, &ndim, &fdum, cdum)) == -1)
{
sprintf(errmsg,
"Error: failed to get dimensionality in file id %d",exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return(EX_FATAL);
}
/* First count up # of elements in the side sets*/
for (i=0;i<num_side_sets;i++)
tot_num_ss_elem += num_elem_per_set[i];
/* Allocate space for the ss element index array */
if (!(ss_elem_ndx=malloc(tot_num_ss_elem*sizeof(int))))
{
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for side set elem sort array for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
/* Sort side set element list into index array - non-destructive */
for (i=0;i<tot_num_ss_elem;i++)
ss_elem_ndx[i] = i; /* init index array to current position */
ex_iqsort(side_sets_elem_list, ss_elem_ndx,tot_num_ss_elem);
/* Allocate space for the element block ids */
if (!(elem_blk_ids=malloc(num_elem_blks*sizeof(int))))
{
free(ss_elem_ndx);
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for element block ids for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
if (ex_get_elem_blk_ids(exoid, elem_blk_ids))
{
free(elem_blk_ids);
free(ss_elem_ndx);
sprintf(errmsg,
"Error: failed to get element block ids in file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,EX_MSG);
return(EX_FATAL);
}
/* Allocate space for the element block params */
if (!(elem_blk_parms=malloc(num_elem_blks*sizeof(struct elem_blk_parm))))
{
free(elem_blk_ids);
free(ss_elem_ndx);
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for element block params for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
elem_ctr = 0;
for (i=0; i<num_elem_blks; i++)
{
/* read in an element block parameter */
if ((ex_get_elem_block (exoid,
elem_blk_ids[i],
elem_type,
&num_elem_in_blk,
&num_nodes_per_elem,
&num_attr)) == -1)
{
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
sprintf(errmsg,
"Error: failed to get element block %d parameters in file id %d",
elem_blk_ids[i], exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,EX_MSG);
return(EX_FATAL);
}
elem_blk_parms[i].num_elem_in_blk = num_elem_in_blk;
elem_blk_parms[i].num_nodes_per_elem = num_nodes_per_elem;
elem_blk_parms[i].num_attr = num_attr;
for (m=0; (size_t)m < strlen(elem_type); m++)
elem_blk_parms[i].elem_type[m] =
(char)toupper((int)elem_type[m]);
elem_blk_parms[i].elem_type[m] = '\0';
if (strncmp(elem_blk_parms[i].elem_type,"CIRCLE",3) == 0)
{
elem_blk_parms[i].elem_type_val = CIRCLE;
/* set side set node stride */
elem_blk_parms[i].num_nodes_per_side = 1;
}
else if (strncmp(elem_blk_parms[i].elem_type,"SPHERE",3) == 0)
{
elem_blk_parms[i].elem_type_val = SPHERE;
/* set side set node stride */
elem_blk_parms[i].num_nodes_per_side = 1;
}
else if (strncmp(elem_blk_parms[i].elem_type,"QUAD",3) == 0)
{
elem_blk_parms[i].elem_type_val = QUAD;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 4)
elem_blk_parms[i].num_nodes_per_side = 2;
else if (elem_blk_parms[i].num_nodes_per_elem == 5)
elem_blk_parms[i].num_nodes_per_side = 2;
else
elem_blk_parms[i].num_nodes_per_side = 3;
}
else if (strncmp(elem_blk_parms[i].elem_type,"TRIANGLE",3) == 0)
{
elem_blk_parms[i].elem_type_val = TRIANGLE;
/* determine side set node stride */
if (ndim == 2) /* 2d TRIs */
{
if (elem_blk_parms[i].num_nodes_per_elem == 3)
elem_blk_parms[i].num_nodes_per_side = 2;
else
elem_blk_parms[i].num_nodes_per_side = 3;
}
else if (ndim == 3) /* 3d TRIs */
{
elem_blk_parms[i].elem_type_val = TRISHELL;
elem_blk_parms[i].num_nodes_per_side =
elem_blk_parms[i].num_nodes_per_elem;
}
}
else if (strncmp(elem_blk_parms[i].elem_type,"SHELL",3) == 0)
{
elem_blk_parms[i].elem_type_val = SHELL;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 2)
{
/* 2d SHELL; same as BEAM or TRUSS or BAR */
elem_blk_parms[i].num_nodes_per_side = 2;
elem_blk_parms[i].elem_type_val = BEAM;
}
else if (elem_blk_parms[i].num_nodes_per_elem == 4)
elem_blk_parms[i].num_nodes_per_side = 4;
else
elem_blk_parms[i].num_nodes_per_side = 8;
}
else if (strncmp(elem_blk_parms[i].elem_type,"HEX",3) == 0)
{
elem_blk_parms[i].elem_type_val = HEX;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 8)
elem_blk_parms[i].num_nodes_per_side = 4;
else if (elem_blk_parms[i].num_nodes_per_elem == 9)
elem_blk_parms[i].num_nodes_per_side = 4;
else if (elem_blk_parms[i].num_nodes_per_elem == 12) /* HEXSHELL */
elem_blk_parms[i].num_nodes_per_side = 4;
else if (elem_blk_parms[i].num_nodes_per_elem == 27)
elem_blk_parms[i].num_nodes_per_side = 9;
else
elem_blk_parms[i].num_nodes_per_side = 8;
}
else if (strncmp(elem_blk_parms[i].elem_type,"TETRA",3) == 0)
{
elem_blk_parms[i].elem_type_val = TETRA;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 4)
elem_blk_parms[i].num_nodes_per_side = 3;
else if (elem_blk_parms[i].num_nodes_per_elem == 8)
elem_blk_parms[i].num_nodes_per_side = 4;
else
elem_blk_parms[i].num_nodes_per_side = 6;
}
else if (strncmp(elem_blk_parms[i].elem_type,"WEDGE",3) == 0)
{
elem_blk_parms[i].elem_type_val = WEDGE;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 6)
elem_blk_parms[i].num_nodes_per_side = 4;
else
elem_blk_parms[i].num_nodes_per_side = 8;
sprintf(errmsg,
"Warning: WEDGE%d is assumed to have %d nodes per face",
elem_blk_parms[i].num_nodes_per_elem,
elem_blk_parms[i].num_nodes_per_side);
ex_err("ex_cvt_nodes_to_sides",errmsg,EX_MSG);
}
else if (strncmp(elem_blk_parms[i].elem_type,"PYRAMID",3) == 0)
{
elem_blk_parms[i].elem_type_val = PYRAMID;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 5)
elem_blk_parms[i].num_nodes_per_side = 4;
else
elem_blk_parms[i].num_nodes_per_side = 8;
sprintf(errmsg,
"Warning: PYRAMID%d is assumed to have %d nodes per face",
elem_blk_parms[i].num_nodes_per_elem,
elem_blk_parms[i].num_nodes_per_side);
ex_err("ex_cvt_nodes_to_sides",errmsg,EX_MSG);
}
else if (strncmp(elem_blk_parms[i].elem_type,"BEAM",3) == 0)
{
elem_blk_parms[i].elem_type_val = BEAM;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 2)
elem_blk_parms[i].num_nodes_per_side = 2;
else
elem_blk_parms[i].num_nodes_per_side = 3;
}
else if ( (strncmp(elem_blk_parms[i].elem_type,"TRUSS",3) == 0) ||
(strncmp(elem_blk_parms[i].elem_type,"BAR",3) == 0) ||
(strncmp(elem_blk_parms[i].elem_type,"EDGE",3) == 0) )
{
elem_blk_parms[i].elem_type_val = TRUSS;
/* determine side set node stride */
if (elem_blk_parms[i].num_nodes_per_elem == 2)
elem_blk_parms[i].num_nodes_per_side = 2;
else
elem_blk_parms[i].num_nodes_per_side = 3;
}
else if (strncmp(elem_blk_parms[i].elem_type,"NULL",3) == 0)
{
elem_blk_parms[i].elem_type_val = '\0';
/* set side set node stride */
elem_blk_parms[i].num_nodes_per_side = 0;
}
else
{ /* unsupported element type; no problem if no sides specified for
this element block */
elem_blk_parms[i].elem_type_val = UNK;
elem_blk_parms[i].num_nodes_per_side = 0;
}
elem_blk_parms[i].elem_blk_id = elem_blk_ids[i]; /* save id */
elem_ctr += elem_blk_parms[i].num_elem_in_blk;
elem_blk_parms[i].elem_ctr = elem_ctr; /* save elem number max */
}
/* Allocate space for the ss element to element block parameter index array */
if (!(ss_parm_ndx=malloc(tot_num_ss_elem*sizeof(int))))
{
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for side set elem parms index for file id %d"
,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
/* Allocate space for the ss element to node list index array */
if (!(ss_elem_node_ndx=malloc((tot_num_ss_elem+1)*sizeof(int))))
{
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for side set elem to node index for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
/* determine if each side set has uniform element types; this will
be used to help determine the stride through the node list
*/
/* Allocate space for same element type flag array*/
if (!(same_elem_type=malloc(num_side_sets*sizeof(int))))
{
free(ss_elem_ndx);
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for element type flag array for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return (EX_FATAL);
}
elem_ctr = num_elem_per_set[0];
same_elem_type[0] = TRUE;
for (i=0,k=0;i<tot_num_ss_elem;i++)
{
for (j=0; j<num_elem_blks; j++)
{
if (side_sets_elem_list[i] <= elem_blk_parms[j].elem_ctr) break;
}
if (i==0) {
el_type = elem_blk_parms[j].elem_type_val;
}
/* determine which side set this element is in; assign to kth side set */
if (i >= elem_ctr) {
elem_ctr += num_elem_per_set[++k];
el_type = elem_blk_parms[j].elem_type_val;
same_elem_type[k] = TRUE;
}
if (el_type != elem_blk_parms[j].elem_type_val) same_elem_type[k] = FALSE;
}
/* Build side set element to node list index and side set element
parameter index.
*/
node_ctr = 0;
elem_ctr = num_elem_per_set[0];
for (i=0,k=0;i<tot_num_ss_elem;i++)
{
for (j=0; j<num_elem_blks; j++)
{
if (side_sets_elem_list[i] <= elem_blk_parms[j].elem_ctr)
{
ss_parm_ndx[i] = j; /* assign parameter block index */
break;
}
}
ss_elem_node_ndx[i] = node_ctr; /* assign node list index */
/* determine which side set this element is in; assign to kth side set */
if (i >= elem_ctr) {
/* skip over NULL side sets */
while (num_elem_per_set[++k] == 0);
elem_ctr += num_elem_per_set[k];
}
/* determine number of nodes per side */
if (((num_nodes_per_set[k] % num_elem_per_set[k]) == 0) &&
(same_elem_type[k])) { /* all side set elements are same type */
node_ctr += num_nodes_per_set[k] /num_elem_per_set[k];
} else {
node_ctr += elem_blk_parms[j].num_nodes_per_side;
}
}
ss_elem_node_ndx[i] = node_ctr; /* assign node list index */
/* All setup, ready to go ... */
elem_ctr=0;
for (j=0; j < tot_num_ss_elem; j++)
{
if (side_sets_elem_list[ss_elem_ndx[j]] > elem_ctr)
{
/* release connectivity array space and get next one */
if (elem_ctr > 0)
free(connect);
/* Allocate space for the connectivity array for new element block */
if (!(connect=
malloc(elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].num_elem_in_blk*
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].num_nodes_per_elem*
sizeof(int))))
{
exerrval = EX_MEMFAIL;
sprintf(errmsg,
"Error: failed to allocate space for connectivity array for file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
/* get connectivity array */
if (ex_get_elem_conn(
exoid,
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
connect) == -1)
{
sprintf(errmsg,
"Error: failed to get connectivity array for elem blk %d for file id %d",
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
elem_ctr = elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_ctr;
}
/* For the first node of each side in side set, using a linear search
(of up to num_nodes_per_elem) of the connectivity array,
locate the node position in the element. The first node position
and the second node position are used with a element type specific
table to determine the side. */
elem_num = side_sets_elem_list[ss_elem_ndx[j]]-1;/* element number 0-based*/
/* calculate the relative element number position in it's block*/
elem_num_pos = elem_num -
(elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_ctr -
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].num_elem_in_blk);
/* calculate the beginning of the node list for this element by
using the ss_elem_node_ndx index into the side_sets_node_index
and adding the element number position * number of nodes per elem */
num_nodes_per_elem =
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].num_nodes_per_elem;
for (n=0; n<num_nodes_per_elem; n++)
{
/* find node in connectivity array that matches first node in side set */
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]] ==
connect[num_nodes_per_elem*(elem_num_pos)+n])
{
switch (elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_type_val)
{
case CIRCLE:
case SPHERE:
{
/* simple case: 1st node number is same as side # */
side_sets_side_list[ss_elem_ndx[j]] = n+1;
break;
}
case QUAD:
case TRIANGLE:
case TRUSS:
case BEAM:
{
/* simple case: 1st node number is same as side # */
side_sets_side_list[ss_elem_ndx[j]] = n+1;
break;
}
case TRISHELL:
{
/* use table to find which node to compare to next */
num_node_per_side = ss_elem_node_ndx[ss_elem_ndx[j]+1] -
ss_elem_node_ndx[ss_elem_ndx[j]];
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(trishell_table[0][2*n]-1)])
{
/* Assume only front or back, no edges... */
side_sets_side_list[ss_elem_ndx[j]] = trishell_table[1][2*n];
}
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(trishell_table[0][2*n+1]-1)])
{
/* Assume only front or back, no edges... */
side_sets_side_list[ss_elem_ndx[j]] = trishell_table[1][2*n+1];
}
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(trishell_table[0][2*n+2]-1)])
{
/* Assume only front or back, no edges... */
side_sets_side_list[ss_elem_ndx[j]] = trishell_table[1][2*n+2];
}
else
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find TRIANGULAR SHELL element %d, node %d in connectivity array %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
break;
}
case SHELL:
{
/* use table to find which node to compare to next */
num_node_per_side = ss_elem_node_ndx[ss_elem_ndx[j]+1] -
ss_elem_node_ndx[ss_elem_ndx[j]];
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(shell_table[0][2*n]-1)])
{
if (num_node_per_side >= 4)
/* 4- or 8-node side (front or back face) */
side_sets_side_list[ss_elem_ndx[j]] = shell_table[1][2*n];
else
/* 2- or 3-node side (edge of shell) */
side_sets_side_list[ss_elem_ndx[j]] = shell_edge_table[1][2*n];
}
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(shell_table[0][2*n+1]-1)])
{
if (num_node_per_side >= 4)
/* 4- or 8-node side (front or back face) */
side_sets_side_list[ss_elem_ndx[j]] = shell_table[1][2*n+1];
else
/* 2- or 3-node side (edge of shell) */
side_sets_side_list[ss_elem_ndx[j]]=shell_edge_table[1][2*n+1];
}
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(shell_table[0][2*n+2]-1)])
{
if (num_node_per_side >= 4)
/* 4- or 8-node side (front or back face) */
side_sets_side_list[ss_elem_ndx[j]] = shell_table[1][2*n+2];
else
/* 2- or 3-node side (edge of shell) */
side_sets_side_list[ss_elem_ndx[j]]=shell_edge_table[1][2*n+2];
}
else
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find SHELL element %d, node %d in connectivity array %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
break;
}
case HEX:
{
/* use table to find which node to compare to next */
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(hex_table[0][3*n]-1)])
side_sets_side_list[ss_elem_ndx[j]] = hex_table[1][3*n];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(hex_table[0][3*n+1]-1)])
side_sets_side_list[ss_elem_ndx[j]] = hex_table[1][3*n+1];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(hex_table[0][3*n+2]-1)])
side_sets_side_list[ss_elem_ndx[j]] = hex_table[1][3*n+2];
else
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find HEX element %d, node %d in connectivity array %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
break;
}
case TETRA:
{
/* use table to find which node to compare to next */
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(tetra_table[0][3*n]-1)])
side_sets_side_list[ss_elem_ndx[j]] = tetra_table[1][3*n];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(tetra_table[0][3*n+1]-1)])
side_sets_side_list[ss_elem_ndx[j]] = tetra_table[1][3*n+1];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(tetra_table[0][3*n+2]-1)])
side_sets_side_list[ss_elem_ndx[j]] = tetra_table[1][3*n+2];
else
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find TETRA element %d, node %d in connectivity array %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
break;
}
case PYRAMID:
{
/* NOTE: PYRAMID elements in side set node lists are currently not supported */
exerrval = EX_BADPARAM;
sprintf(errmsg,
"ERROR: unsupported PYRAMID element found in side set node list in file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
case WEDGE:
{
#if 1
/* NOTE: WEDGE elements in side set node lists are currently not supported */
exerrval = EX_BADPARAM;
sprintf(errmsg,
"ERROR: unsupported WEDGE element found in side set node list in file id %d",
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
#else
/* use wedge_table to find which node to compare to next */
/* This section is commented out because Wedges are no longer supported !!!*/
if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(wedge_table[0][3*n]-1)])
side_sets_side_list[ss_elem_ndx[j]] = wedge_table[1][3*n];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(wedge_table[0][3*n+1]-1)])
side_sets_side_list[ss_elem_ndx[j]] = wedge_table[1][3*n+1];
else if (side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1] ==
connect[num_nodes_per_elem*(elem_num_pos)+
(wedge_table[0][3*n+2]-1)])
side_sets_side_list[ss_elem_ndx[j]] = wedge_table[1][3*n+2];
else
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find WEDGE element %d, node %d in connectivity array %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]+1],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
break;
#endif
}
default:
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: %s is an unsupported element type",
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_type);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
return(EX_FATAL);
}
}
break; /* done with this element */
}
}
if (n >= num_nodes_per_elem) /* did we find the node? */
{
exerrval = EX_BADPARAM;
sprintf(errmsg,
"Error: failed to find element %d, node %d in element block %d for file id %d",
side_sets_elem_list[ss_elem_ndx[j]],
side_sets_node_list[ss_elem_node_ndx[ss_elem_ndx[j]]],
elem_blk_parms[ss_parm_ndx[ss_elem_ndx[j]]].elem_blk_id,
exoid);
ex_err("ex_cvt_nodes_to_sides",errmsg,exerrval);
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_FATAL);
}
}
/* All done: release connectivity array space, element block ids array,
element block parameters array, and side set element index array */
free(connect);
free(ss_elem_node_ndx);
free(ss_parm_ndx);
free(elem_blk_parms);
free(elem_blk_ids);
free(ss_elem_ndx);
return (EX_NOERR);
}