19 #include "libmesh/libmesh_config.h" 
   20 #include "libmesh/libmesh_logging.h" 
   21 #include "libmesh/dof_map.h" 
   22 #include "libmesh/elem.h" 
   23 #include "libmesh/dyna_io.h" 
   24 #include "libmesh/mesh_base.h" 
   25 #include "libmesh/int_range.h" 
   62   for (
unsigned int i=1; i != 2; ++i)
 
   75                                    {0, 4, 1, 7, 8, 5, 3, 6, 2}));
 
   78                                    {0, 1, 3, 2, 4, 5, 7, 6}));
 
   80                                    { 0,  8,  1, 11, 20,  9,  3, 10,  2,
 
   81                                     12, 21, 13, 24, 26, 22, 15, 23, 14,
 
   82                                      4, 16,  5, 19, 25, 17,  7, 18,  6}));
 
   96   dyna_type(dyna_type_in),
 
  102   std::iota(nodes.begin(), nodes.end(), 0);
 
  111    std::vector<unsigned int> && nodes_in) :
 
  113   dyna_type(dyna_type_in),
 
  123   constraint_rows_broadcast (false)
 
  131   std::ifstream in (
name.c_str());
 
  164     ELEM_SUBBLOCK_HEADER,
 
  178   FileSection section = FILE_HEADER;
 
  183   std::vector<dyna_int_type> 
 
  190   std::vector<dyna_int_type> 
 
  191     n_coef_vecs_in_subblock, n_coef_comp;
 
  192   unsigned char weight_index = 0;
 
  194                 n_elem_blocks_read = 0,
 
  196                 n_elem_nodes_read = 0,
 
  197                 n_elem_cvids_read = 0,
 
  198                 n_coef_headers_read = 0,
 
  199                 n_coef_blocks_read = 0,
 
  200                 n_coef_comp_read = 0,
 
  201                 n_coef_vecs_read = 0;
 
  208   std::vector<Real> spline_weights;
 
  213   std::vector<std::vector<std::vector<dof_id_type>>> elem_global_nodes;
 
  220   std::vector<std::vector<std::vector<Real>>> dense_constraint_vecs;
 
  224   std::vector<std::vector<std::vector<dof_id_type>>> elem_constraint_rows;
 
  235           if (s.find(
"B E X T 2.0") == static_cast<std::string::size_type>(0))
 
  237             libmesh_assert_equal_to(section, FILE_HEADER);
 
  238             section = PATCH_HEADER;
 
  243           if (s.find(
"$#") == static_cast<std::string::size_type>(0))
 
  247           if (s.find_first_not_of(
" \t") == std::string::npos)
 
  251           std::stringstream stream(s);
 
  255             stream >> n_spline_nodes;
 
  257             stream >> n_coef_vec;
 
  258             stream >> weight_control_flag;
 
  260               libmesh_error_msg(
"Failure to parse patch header\n");
 
  263             spline_weights.resize(n_spline_nodes);
 
  265             if (weight_control_flag)
 
  267                 weight_index = cast_int<unsigned char>
 
  273             section = NODE_LINES;
 
  277               std::array<dyna_fp_type, 4> xyzw;
 
  283               if (weight_control_flag)
 
  284                 spline_weights[n_nodes_read] = xyzw[3];
 
  298               libmesh_error_msg(
"Failure to parse node line\n");
 
  300             if (n_nodes_read >= n_spline_nodes)
 
  301               section = N_ELEM_SUBBLOCKS;
 
  303           case N_ELEM_SUBBLOCKS:
 
  304             stream >> n_elem_blocks;
 
  306               libmesh_error_msg(
"Failure to parse n_elem_blocks\n");
 
  308             block_elem_type.resize(n_elem_blocks);
 
  309             block_n_elem.resize(n_elem_blocks);
 
  310             block_n_nodes.resize(n_elem_blocks);
 
  311             block_n_coef_vec.resize(n_elem_blocks);
 
  312             block_p.resize(n_elem_blocks);
 
  313             block_dim.resize(n_elem_blocks);
 
  315             elem_global_nodes.resize(n_elem_blocks);
 
  316             elem_constraint_rows.resize(n_elem_blocks);
 
  318             n_elem_blocks_read = 0;
 
  319             section = ELEM_SUBBLOCK_HEADER;
 
  321           case ELEM_SUBBLOCK_HEADER:
 
  322             stream >> block_elem_type[n_elem_blocks_read];
 
  323             stream >> block_n_elem[n_elem_blocks_read];
 
  324             stream >> block_n_nodes[n_elem_blocks_read];
 
  325             stream >> block_n_coef_vec[n_elem_blocks_read];
 
  326             stream >> block_p[n_elem_blocks_read];
 
  329               libmesh_error_msg(
"Failure to parse elem block\n");
 
  331             block_dim[n_elem_blocks_read] = 1; 
 
  334             stream >> block_other_p;
 
  337                 block_dim[n_elem_blocks_read] = 2; 
 
  339                 if (block_other_p != block_p[n_elem_blocks_read])
 
  340                   libmesh_not_implemented(); 
 
  342                 stream >> block_other_p;
 
  345                     block_dim[n_elem_blocks_read] = 3; 
 
  347                     if (block_other_p != block_p[n_elem_blocks_read])
 
  348                       libmesh_not_implemented();
 
  353               auto & block_global_nodes = elem_global_nodes[n_elem_blocks_read];
 
  354               auto & block_constraint_rows = elem_constraint_rows[n_elem_blocks_read];
 
  356               block_global_nodes.resize(block_n_elem[n_elem_blocks_read]);
 
  357               block_constraint_rows.resize(block_n_elem[n_elem_blocks_read]);
 
  360                    (0, block_n_elem[n_elem_blocks_read]))
 
  362                   block_global_nodes[e].resize(block_n_nodes[n_elem_blocks_read]);
 
  363                   block_constraint_rows[e].resize(block_n_coef_vec[n_elem_blocks_read]);
 
  367             n_elem_blocks_read++;
 
  368             if (n_elem_blocks_read == n_elem_blocks)
 
  370                 n_elem_blocks_read = 0;
 
  372                 section = ELEM_NODES_LINES;
 
  375           case ELEM_NODES_LINES:
 
  377               const int end_node_to_read =
 
  378                 std::min(block_n_nodes[n_elem_blocks_read], n_elem_nodes_read + 
max_ints_per_line);
 
  379               for (; n_elem_nodes_read != end_node_to_read; ++n_elem_nodes_read)
 
  384                   elem_global_nodes[n_elem_blocks_read][n_elems_read][n_elem_nodes_read] = node_id;
 
  390                     libmesh_error_msg(
"Failure to parse elem nodes\n");
 
  393               if (n_elem_nodes_read == block_n_nodes[n_elem_blocks_read])
 
  395                   n_elem_nodes_read = 0;
 
  396                   section = ELEM_COEF_VEC_IDS;
 
  400           case ELEM_COEF_VEC_IDS:
 
  402               const int end_cvid_to_read =
 
  403                 std::min(block_n_coef_vec[n_elem_blocks_read], n_elem_cvids_read + 
max_ints_per_line);
 
  404               for (; n_elem_cvids_read != end_cvid_to_read; ++n_elem_cvids_read)
 
  410                   elem_constraint_rows[n_elem_blocks_read][n_elems_read][n_elem_cvids_read] = node_cvid;
 
  416                     libmesh_error_msg(
"Failure to parse elem cvids\n");
 
  418               if (n_elem_cvids_read == block_n_nodes[n_elem_blocks_read])
 
  420                   n_elem_cvids_read = 0;
 
  422                   section = ELEM_NODES_LINES; 
 
  423                   if (n_elems_read == block_n_elem[n_elem_blocks_read])
 
  426                       n_elem_blocks_read++;
 
  427                       if (n_elem_blocks_read == n_elem_blocks)
 
  428                         section = N_COEF_BLOCKS; 
 
  435               stream >> n_dense_coef_vec_blocks;
 
  437               stream >> n_sparse_coef_vec_blocks;
 
  440                 libmesh_error_msg(
"Failure to parse n_*_coef_vec_blocks\n");
 
  442               if (n_sparse_coef_vec_blocks != 0)
 
  443                 libmesh_not_implemented();
 
  445               dense_constraint_vecs.resize(n_dense_coef_vec_blocks);
 
  446               n_coef_vecs_in_subblock.resize(n_dense_coef_vec_blocks);
 
  447               n_coef_comp.resize(n_dense_coef_vec_blocks);
 
  449               section = N_VECS_PER_BLOCK;
 
  452           case N_VECS_PER_BLOCK:
 
  453             stream >> n_coef_vecs_in_subblock[n_coef_headers_read];
 
  454             stream >> n_coef_comp[n_coef_headers_read];
 
  457               libmesh_error_msg(
"Failure to parse dense coef subblock header\n");
 
  459             dense_constraint_vecs[n_coef_headers_read].resize
 
  460               (n_coef_vecs_in_subblock[n_coef_headers_read]);
 
  462             for (
auto & vec : dense_constraint_vecs[n_coef_headers_read])
 
  463               vec.resize(n_coef_comp[n_coef_headers_read]);
 
  465             n_coef_headers_read++;
 
  466             if (n_coef_headers_read == n_dense_coef_vec_blocks)
 
  468                 n_coef_headers_read = 0;
 
  469                 section = COEF_VEC_COMPONENTS;
 
  472           case COEF_VEC_COMPONENTS:
 
  475                 dense_constraint_vecs[n_coef_blocks_read][n_coef_vecs_read];
 
  477               const int end_coef_to_read =
 
  478                 std::min(n_coef_comp[n_coef_blocks_read],
 
  480               for (; n_coef_comp_read != end_coef_to_read; ++n_coef_comp_read)
 
  485                   current_vec[n_coef_comp_read] = coef_comp;
 
  491                     libmesh_error_msg(
"Failure to parse coefficients\n");
 
  493               if (n_coef_comp_read == n_coef_comp[n_coef_blocks_read])
 
  495                   n_coef_comp_read = 0;
 
  497                   if (n_coef_vecs_read == n_coef_vecs_in_subblock[n_coef_blocks_read])
 
  499                       n_coef_vecs_read = 0;
 
  500                       n_coef_blocks_read++;
 
  501                       if (n_coef_blocks_read == n_dense_coef_vec_blocks)
 
  502                         section = END_OF_FILE;
 
  511           if (section == END_OF_FILE)
 
  515         libmesh_error_msg(
"Premature end of file");
 
  517         libmesh_error_msg(
"Input stream failure! Perhaps the file does not exist?");
 
  521   for (
auto coef_vec_block :
 
  524       auto & dcv0 = dense_constraint_vecs[0];
 
  525       auto & dcvi = dense_constraint_vecs[coef_vec_block];
 
  526       dcv0.insert(dcv0.end(),
 
  527                   std::make_move_iterator(dcvi.begin()),
 
  528                   std::make_move_iterator(dcvi.end()));
 
  530   dense_constraint_vecs.resize(1);
 
  534   std::vector<std::vector<std::vector<std::vector<Real>>>> elem_constraint_mat(n_elem_blocks);
 
  540   std::map<std::vector<std::pair<dof_id_type, Real>>, 
Node *> local_nodes;
 
  544       elem_constraint_mat[block_num].resize(block_n_elem[block_num]);
 
  552                                                   block_dim[block_num],
 
  553                                                   block_p[block_num]));
 
  558               (
"Element of type " << block_elem_type[block_num] <<
 
  559                " dim " << block_dim[block_num] <<
 
  560                " degree " << block_p[block_num] << 
" not found!");
 
  564           libmesh_assert_equal_to(elem->
dim(), block_dim[block_num]);
 
  566           auto & my_constraint_rows = elem_constraint_rows[block_num][elem_num];
 
  567           auto & my_global_nodes    = elem_global_nodes[block_num][elem_num];
 
  568           auto & my_constraint_mat  = elem_constraint_mat[block_num][elem_num];
 
  570           my_constraint_mat.resize(block_n_coef_vec[block_num]);
 
  571           for (
auto spline_node_index :
 
  573             my_constraint_mat[spline_node_index].resize(elem->
n_nodes());
 
  575           for (
auto spline_node_index :
 
  580                 my_constraint_rows[spline_node_index];
 
  584               for (; elem_coef_vec_index >= first_block_coef_vec &&
 
  585                    coef_block_num != n_dense_coef_vec_blocks; ++coef_block_num)
 
  587                   first_block_coef_vec += n_coef_vecs_in_subblock[coef_block_num];
 
  591               if (coef_block_num == n_dense_coef_vec_blocks &&
 
  592                   first_block_coef_vec <= elem_coef_vec_index)
 
  593                 libmesh_error_msg(
"Can't find valid constraint coef vector");
 
  598                   n_coef_comp[coef_block_num])
 
  599                 libmesh_error_msg(
"Found " <<
 
  600                                   n_coef_comp[coef_block_num] <<
 
  601                                   " constraint coef vectors for " <<
 
  604               for (
auto elem_node_index :
 
  606                 my_constraint_mat[spline_node_index][elem_node_index] =
 
  607                   dense_constraint_vecs[0][elem_coef_vec_index][elem_node_index];
 
  610           for (
auto elem_node_index :
 
  618               std::vector<std::pair<dof_id_type, Real>> key;
 
  620               for (
auto spline_node_index :
 
  624                     my_constraint_rows[spline_node_index];
 
  627                     dense_constraint_vecs[0][elem_coef_vec_index][elem_node_index];
 
  631                   libmesh_assert_greater(my_global_nodes[spline_node_index],
 
  633                   global_node_idx = my_global_nodes[spline_node_index];
 
  636                     key.push_back(std::make_pair(global_node_idx, coef));
 
  639               auto local_node_it = local_nodes.find(key);
 
  641               if (local_node_it != local_nodes.end())
 
  643                   local_node_it->second;
 
  648                   std::vector<std::pair<dof_id_type, Real>> constraint_row;
 
  650                   for (
auto spline_node_index :
 
  654                         my_global_nodes[spline_node_index];
 
  657                         my_constraint_rows[spline_node_index];
 
  662                         dense_constraint_vecs[0][elem_coef_vec_index][elem_node_index];
 
  664                       w += coef * spline_weights[my_node_idx];
 
  666                       constraint_row.push_back(std::make_pair(spline_node->
id(), coef));
 
  670                   if (weight_control_flag)
 
  672                   local_nodes[key] = n;
 
  686                                     unsigned int sys_num,
 
  687                                     unsigned int var_num)
 
  689 #ifdef LIBMESH_ENABLE_CONSTRAINTS 
  696     libmesh_not_implemented();
 
  714       for (
auto pr : node_row.second)
 
  719           dc_row[spline_dof_id] = pr.second;
 
  725   libmesh_not_implemented();