inline stk::mesh::Entity get_face_between_element_ids(stk::mesh::ElemElemGraph& graph, stk::mesh::BulkData& bulkData, stk::mesh::EntityId elem1Id, stk::mesh::EntityId elem2Id)
{
    stk::mesh::Entity elem1 = bulkData.get_entity(stk::topology::ELEM_RANK, elem1Id);
    stk::mesh::Entity elem2 = bulkData.get_entity(stk::topology::ELEM_RANK, elem2Id);

    bool isElem1LocallyOwnedAndValid = bulkData.is_valid(elem1) && bulkData.bucket(elem1).owned();
    bool isElem2LocallyOwnedAndValid = bulkData.is_valid(elem2) && bulkData.bucket(elem2).owned();

    stk::mesh::Entity face_between_elem1_and_elem2;

    if(isElem1LocallyOwnedAndValid && isElem2LocallyOwnedAndValid)
    {
        int side = graph.get_side_from_element1_to_locally_owned_element2(elem1, elem2);
        EXPECT_TRUE(side != -1);
        face_between_elem1_and_elem2 = stk::mesh::impl::get_side_for_element(bulkData, elem1, side);
    }
    else if(isElem1LocallyOwnedAndValid)
    {
        int side = graph.get_side_from_element1_to_remote_element2(elem1, elem2Id);
        EXPECT_TRUE(side != -1);
        face_between_elem1_and_elem2 = stk::mesh::impl::get_side_for_element(bulkData, elem1, side);
    }
    else if(isElem2LocallyOwnedAndValid)
    {
        int side = graph.get_side_from_element1_to_remote_element2(elem2, elem1Id);
        EXPECT_TRUE(side != -1);
        face_between_elem1_and_elem2 = stk::mesh::impl::get_side_for_element(bulkData, elem2, side);
    }
    return face_between_elem1_and_elem2;
}
예제 #2
0
// ========================================================================
void process_surface_entity(const Ioss::SideSet* sset ,
                            stk::mesh::BulkData & bulk)
{
    assert(sset->type() == Ioss::SIDESET);

    const stk::mesh::MetaData& meta = stk::mesh::MetaData::get(bulk);
    const stk::mesh::EntityRank element_rank = stk::topology::ELEMENT_RANK;

    int block_count = sset->block_count();
    for (int i=0; i < block_count; i++) {
        Ioss::SideBlock *block = sset->get_block(i);
        if (stk::io::include_entity(block)) {
            std::vector<int> side_ids ;
            std::vector<int> elem_side ;

            stk::mesh::Part * const side_block_part = meta.get_part(block->name());
            stk::mesh::EntityRank side_rank = side_block_part->primary_entity_rank();

            block->get_field_data("ids", side_ids);
            block->get_field_data("element_side", elem_side);

            assert(side_ids.size() * 2 == elem_side.size());
            stk::mesh::PartVector add_parts( 1 , side_block_part );

            size_t side_count = side_ids.size();
            std::vector<stk::mesh::Entity> sides(side_count);
            for(size_t is=0; is<side_count; ++is) {

                stk::mesh::Entity const elem = bulk.get_entity(element_rank, elem_side[is*2]);

                // If NULL, then the element was probably assigned to an
                // element block that appears in the database, but was
                // subsetted out of the analysis mesh. Only process if
                // non-null.
                if (bulk.is_valid(elem)) {
                    // Ioss uses 1-based side ordinal, stk::mesh uses 0-based.
                    // Hence the '-1' in the following line.
                    int side_ordinal = elem_side[is*2+1] - 1 ;

                    stk::mesh::Entity side = stk::mesh::Entity();
                    if (side_rank == 2) {
                        side = stk::mesh::declare_element_side(bulk, side_ids[is], elem, side_ordinal);
                    } else {
                        side = stk::mesh::declare_element_edge(bulk, side_ids[is], elem, side_ordinal);
                    }
                    bulk.change_entity_parts( side, add_parts );
                    sides[is] = side;
                } else {
                    sides[is] = stk::mesh::Entity();
                }
            }

            const stk::mesh::FieldBase *df_field = stk::io::get_distribution_factor_field(*side_block_part);

            if (df_field != NULL) {
                stk::io::field_data_from_ioss(bulk, df_field, sides, block, "distribution_factors");
            }
        }
    }
}
예제 #3
0
stk::mesh::Entity create_side_and_add_to_shared_entity_list(stk::mesh::Entity element, stk::mesh::EntityRank side_rank, const stk::mesh::EntityVector& nodes, const stk::mesh::shared_entity_type &shared_entity_other_proc,
        stk::mesh::BulkData& bulkData, std::vector<stk::mesh::shared_entity_type>& shared_entities_this_proc, int other_proc_id, stk::mesh::Part& root_topo_part)
{
    stk::mesh::Entity side = stk::unit_test_util::declare_element_to_sub_topology_with_nodes(bulkData, element, nodes, shared_entity_other_proc.global_key.id(), side_rank, root_topo_part);
    ThrowRequireWithSierraHelpMsg(bulkData.is_valid(side));
    add_side_to_shared_entities(side, shared_entities_this_proc, shared_entity_other_proc, other_proc_id);
    return side;
}
예제 #4
0
 void convert_elem_sides_pairs_into_sideset(const stk::mesh::BulkData& bulk, const std::vector<int>& elem_side, stk::mesh::SideSet& sideset)
 {
     for(size_t is=0; is<elem_side.size() / 2; ++is)
     {
         stk::mesh::Entity const elem = bulk.get_entity(stk::topology::ELEMENT_RANK, elem_side[is*2]);
         if (bulk.is_valid(elem))
             sideset.push_back(add_elem_side_pair(elem, elem_side[is*2+1]));
     }
 }
예제 #5
0
inline void test_num_faces_on_this_element(const stk::mesh::BulkData& bulkData, stk::mesh::EntityId id, size_t gold_num_faces_this_elem)
{
    stk::mesh::Entity element = bulkData.get_entity(stk::topology::ELEM_RANK, id);
    if(bulkData.is_valid(element))
    {
        unsigned num_faces_this_elem = bulkData.num_faces(element);
        EXPECT_EQ(gold_num_faces_this_elem, num_faces_this_elem);
    }
}
void performNodalMeshReduction(
    stk::mesh::Part &samplePart,
    stk::mesh::BulkData& bulkData)
{
  const stk::mesh::MetaData &metaData = stk::mesh::MetaData::get(bulkData);

  std::vector<stk::mesh::Entity> sampleNodes;
  stk::mesh::get_selected_entities(samplePart, bulkData.buckets(stk::topology::NODE_RANK), sampleNodes);

  const stk::mesh::Selector locallyOwned = stk::mesh::MetaData::get(bulkData).locally_owned_part();

  std::vector<stk::mesh::Entity> relatedEntities;
  typedef std::vector<stk::mesh::Entity>::const_iterator EntityIterator;
  for (EntityIterator it(sampleNodes.begin()), it_end(sampleNodes.end()); it != it_end; ++it) {
    for (stk::mesh::EntityRank r = stk::topology::NODE_RANK; r < metaData.entity_rank_count(); ++r) {
      stk::mesh::Entity const* relations = bulkData.begin(*it, r);
      const int num_rels = bulkData.num_connectivity(*it, r);
      for (int i = 0; i < num_rels; ++i) {
        stk::mesh::Entity relatedEntity = relations[i];
        if (bulkData.is_valid(relatedEntity) && locallyOwned(bulkData.bucket(relatedEntity))) {
          relatedEntities.push_back(relatedEntity);
        }
      }
    }
  }
  std::sort(relatedEntities.begin(), relatedEntities.end(), stk::mesh::EntityLess(bulkData));
  relatedEntities.erase(
      std::unique(relatedEntities.begin(), relatedEntities.end()),
      relatedEntities.end());

  std::vector<stk::mesh::Entity> sampleClosure;
  stk::mesh::find_closure(bulkData, relatedEntities, sampleClosure);

  // Keep only the closure, remove the rest, by decreasing entityRanks
  {
    const stk::mesh::Selector ownedOrShared = metaData.locally_owned_part() | metaData.globally_shared_part();
    EntityIterator allKeepersEnd(sampleClosure.end());
    const EntityIterator allKeepersBegin(sampleClosure.begin());
    for (size_t candidateRankCount = metaData.entity_rank_count(); candidateRankCount > 0; --candidateRankCount) {
      const stk::mesh::EntityRank candidateRank = static_cast<stk::mesh::EntityRank>(candidateRankCount - 1);
      const EntityIterator keepersBegin = std::lower_bound(allKeepersBegin, allKeepersEnd,
                                                           stk::mesh::EntityKey(candidateRank, 0),
                                                           stk::mesh::EntityLess(bulkData));
      const EntityIterator keepersEnd = allKeepersEnd;
      std::vector<stk::mesh::Entity> candidates;
      stk::mesh::get_selected_entities(ownedOrShared, bulkData.buckets(candidateRank), candidates);
      {
        BulkModification modification(bulkData);
        std::set_difference(candidates.begin(), candidates.end(),
                            keepersBegin.base(), keepersEnd.base(),
                            EntityDestructor(modification),
                            stk::mesh::EntityLess(bulkData));
      }
      allKeepersEnd = keepersBegin;
    }
  }
}
예제 #7
0
stk::mesh::GraphEdge unpack_edge(stk::CommSparse& comm, const stk::mesh::BulkData& bulkData, const ElemElemGraph& graph, int proc_id)
{
    stk::mesh::EntityId id1 = 0, id2 = 0;
    unsigned side1 = 0, side2 = 0;
    comm.recv_buffer(proc_id).unpack<stk::mesh::EntityId>(id1);
    comm.recv_buffer(proc_id).unpack<unsigned>(side1);
    comm.recv_buffer(proc_id).unpack<stk::mesh::EntityId>(id2);
    comm.recv_buffer(proc_id).unpack<unsigned>(side2);

    stk::mesh::Entity element = bulkData.get_entity(stk::topology::ELEM_RANK, id2);
    ThrowRequireWithSierraHelpMsg(bulkData.is_valid(element));

    stk::mesh::impl::LocalId localId2 = graph.get_local_element_id(element);
    stk::mesh::GraphEdge edge(localId2, side2, -id1, side1);
    return edge;
}
void addNodesToPart(
    const Teuchos::ArrayView<const stk::mesh::EntityId> &nodeIds,
    stk::mesh::Part &samplePart,
    stk::mesh::BulkData& bulkData)
{
  const stk::mesh::PartVector samplePartVec(1, &samplePart);
  const stk::mesh::Selector locallyOwned = stk::mesh::MetaData::get(bulkData).locally_owned_part();

  BulkModification mod(bulkData);
  typedef Teuchos::ArrayView<const stk::mesh::EntityId>::const_iterator Iter;
  for (Iter it = nodeIds.begin(), it_end = nodeIds.end(); it != it_end; ++it) {
    stk::mesh::Entity node = bulkData.get_entity(stk::topology::NODE_RANK, *it);
    if (bulkData.is_valid(node) && locallyOwned(bulkData.bucket(node))) {
      bulkData.change_entity_parts(node, samplePartVec);
    }
  }
}
예제 #9
0
// ========================================================================
void process_nodesets(Ioss::Region &region, stk::mesh::BulkData &bulk)
{
    // Should only process nodes that have already been defined via the element
    // blocks connectivity lists.
    const Ioss::NodeSetContainer& node_sets = region.get_nodesets();

    for(Ioss::NodeSetContainer::const_iterator it = node_sets.begin();
            it != node_sets.end(); ++it) {
        Ioss::NodeSet *entity = *it;

        if (stk::io::include_entity(entity)) {
            const std::string & name = entity->name();
            const stk::mesh::MetaData& meta = stk::mesh::MetaData::get(bulk);
            stk::mesh::Part* const part = meta.get_part(name);
            STKIORequire(part != NULL);
            stk::mesh::PartVector add_parts( 1 , part );

            std::vector<int> node_ids ;
            int node_count = entity->get_field_data("ids", node_ids);

            std::vector<stk::mesh::Entity> nodes(node_count);
            for(int i=0; i<node_count; ++i) {
                nodes[i] = bulk.get_entity( stk::topology::NODE_RANK, node_ids[i] );
                if (bulk.is_valid(nodes[i])) {
                    bulk.declare_entity(stk::topology::NODE_RANK, node_ids[i], add_parts );
                }
            }

            /** \todo REFACTOR Application would probably store this field
             * (and others) somewhere after the declaration instead of
             * looking it up each time it is needed.
             */
            stk::mesh::Field<double> *df_field =
                meta.get_field<stk::mesh::Field<double> >(stk::topology::NODE_RANK, "distribution_factors");

            if (df_field != NULL) {
                stk::io::field_data_from_ioss(bulk, df_field, nodes, entity, "distribution_factors");
            }
        }
    }
}
예제 #10
0
inline size_t get_number_sides_in_sideset(const stk::mesh::BulkData& bulk,
                                          int sideset_id,
                                          stk::mesh::Selector selector,
                                          stk::topology stk_element_topology,
                                          const stk::mesh::BucketVector& buckets)
{
    if (bulk.has_sideset_data())
    {
        selector &= ( bulk.mesh_meta_data().locally_owned_part() | bulk.mesh_meta_data().globally_shared_part());

        size_t num_sides = 0;

        const stk::mesh::SideSet& sset = bulk.get_sideset_data(sideset_id);

        for(const stk::mesh::SideSetEntry& elem_and_side : sset)
        {
            stk::mesh::Entity element = elem_and_side.element;
            stk::mesh::Entity side = stk::mesh::get_side_entity_for_elem_side_pair(bulk, element, elem_and_side.side);
            if(bulk.is_valid(side))
            {
                if(selector(bulk.bucket(side)))
                {
                    if(stk_element_topology == stk::topology::INVALID_TOPOLOGY ||
                       stk_element_topology == bulk.bucket(element).topology())
                    {
                        ++num_sides;
                    }
                }
            }
        }

        return num_sides;
    }
    else
    {
        selector &= bulk.mesh_meta_data().locally_owned_part();
        return count_selected_entities(selector, buckets);
    }
}
예제 #11
0
void fill_element_and_side_ids(Ioss::GroupingEntity & io,
                               stk::mesh::Part * const part,
                               const stk::mesh::BulkData & bulk_data,
                               stk::topology stk_element_topology,
                               const stk::mesh::Selector *subset_selector,
                               stk::mesh::EntityVector &sides,
                               std::vector<INT>& elem_side_ids)
{
    if (bulk_data.has_sideset_data())
    {
        const stk::mesh::SideSet& sset = bulk_data.get_sideset_data(part->id());
        size_t num_sides = sset.size();
        elem_side_ids.reserve(num_sides*2);

        stk::mesh::Selector selector = *part & ( bulk_data.mesh_meta_data().locally_owned_part() | bulk_data.mesh_meta_data().globally_shared_part() );
        if(subset_selector)
            selector &= *subset_selector;

        for(size_t i=0;i<sset.size();++i)
        {
            stk::mesh::Entity element = sset[i].element;
            stk::mesh::EntityId elemId = bulk_data.identifier(element);
            int zero_based_side_ord = sset[i].side;
            stk::mesh::Entity side = stk::mesh::get_side_entity_for_elem_id_side_pair_of_rank(bulk_data, elemId, zero_based_side_ord, bulk_data.mesh_meta_data().side_rank());
            if(bulk_data.is_valid(side))
            {
                if(selector(bulk_data.bucket(side)))
                {
                    if(bulk_data.bucket(element).topology() == stk_element_topology)
                    {
                        elem_side_ids.push_back(elemId);
                        elem_side_ids.push_back(zero_based_side_ord+1);
                        sides.push_back(side);
                    }
                }
            }
        }
    }
    else
    {
        const stk::mesh::MetaData & meta_data = stk::mesh::MetaData::get(*part);

        stk::mesh::EntityRank type = part_primary_entity_rank(*part);
        size_t num_sides = get_entities(*part, type, bulk_data, sides, false, subset_selector);
        elem_side_ids.reserve(num_sides * 2);

        stk::mesh::EntityRank elem_rank = stk::topology::ELEMENT_RANK;

        for(size_t i = 0; i < num_sides; ++i)
        {
            std::vector<stk::mesh::Entity> side;
            side.push_back(sides[i]);
            std::vector<stk::mesh::Entity> side_elements;
            std::vector<stk::mesh::Entity> side_nodes(bulk_data.begin_nodes(sides[i]), bulk_data.end_nodes(sides[i]));

            get_entities_through_relations(bulk_data, side_nodes, elem_rank, side_elements);
            const size_t num_side_elem = side_elements.size();

            std::sort(side_elements.begin(), side_elements.end(), stk::mesh::EntityLess(bulk_data));

            stk::mesh::Entity suitable_elem = stk::mesh::Entity();
            stk::mesh::ConnectivityOrdinal suitable_ordinal = stk::mesh::INVALID_CONNECTIVITY_ORDINAL;
            for(size_t j = 0; j < num_side_elem; ++j)
            {
                const stk::mesh::Entity elem = side_elements[j];
                const stk::mesh::Bucket &elemBucket = bulk_data.bucket(elem);
                const bool isSelectingEverything = subset_selector == NULL;
                const bool isElementBeingOutput = (isSelectingEverything || (*subset_selector)(elemBucket))
                                                  && elemBucket.member(meta_data.locally_owned_part());
                if(isElementBeingOutput)
                {
                    const stk::mesh::Entity * elem_sides = bulk_data.begin(elem, type);
                    stk::mesh::ConnectivityOrdinal const * side_ordinal = bulk_data.begin_ordinals(elem, type);
                    const size_t num_elem_sides = bulk_data.num_connectivity(elem, type);
                    for(size_t k = 0; k < num_elem_sides; ++k)
                    {
                        if(elem_sides[k] == side[0])
                        {
                            suitable_elem = elem;
                            suitable_ordinal = side_ordinal[k];
                            break;
                        }
                    }
                }
            }

            if(!bulk_data.is_valid(suitable_elem))
            {
                std::ostringstream oss;
                oss << "ERROR, no suitable element found";
                throw std::runtime_error(oss.str());
            }

            elem_side_ids.push_back(bulk_data.identifier(suitable_elem));
            elem_side_ids.push_back(suitable_ordinal + 1); // Ioss is 1-based, mesh is 0-based.
        }
    }
}
예제 #12
0
void fixup_ghosted_to_shared_nodes(stk::mesh::BulkData & bulk)
{
    stk::mesh::EntityVector ghosted_nodes_that_are_now_shared;
    find_ghosted_nodes_that_need_to_be_shared(bulk, ghosted_nodes_that_are_now_shared);

    stk::CommSparse comm(bulk.parallel());

    for (int phase=0;phase<2;++phase)
    {
        for (size_t i = 0; i < ghosted_nodes_that_are_now_shared.size(); ++i)
        {
            stk::mesh::Entity node = ghosted_nodes_that_are_now_shared[i];
            int proc = bulk.parallel_owner_rank(node);
            comm.send_buffer(proc).pack<stk::mesh::EntityKey>(bulk.entity_key(node));
        }
        if (phase == 0 )
        {
            comm.allocate_buffers();
        }
        else
        {
            comm.communicate();
        }
    }

    stk::mesh::EntityVector sharedNodes;
    for (int process=0;process<bulk.parallel_size();++process)
    {
        while(comm.recv_buffer(process).remaining())
        {
            stk::mesh::EntityKey key;
            comm.recv_buffer(process).unpack<stk::mesh::EntityKey>(key);

            stk::mesh::Entity entity = bulk.get_entity(key);
            if ( bulk.state(entity) != stk::mesh::Deleted && bulk.is_valid(entity) )
            {
                bulk.add_node_sharing(entity, process);
                sharedNodes.push_back(entity);
            }
        }
    }
/////////////////////////

    stk::CommSparse commSecondStage(bulk.parallel());
    for (int phase=0;phase<2;++phase)
    {
        for (size_t i=0;i<sharedNodes.size();++i)
        {
            std::vector<int> procs;
            stk::mesh::EntityKey key = bulk.entity_key(sharedNodes[i]);
            bulk.comm_shared_procs(key, procs);
            for (size_t j=0;j<procs.size();++j)
            {
                if ( procs[j] != bulk.parallel_rank() )
                {
                    commSecondStage.send_buffer(procs[j]).pack<int>(bulk.parallel_rank()).pack<stk::mesh::EntityKey>(key);
                    for (size_t k=0;k<procs.size();++k)
                    {
                        commSecondStage.send_buffer(procs[j]).pack<int>(procs[k]).pack<stk::mesh::EntityKey>(key);
                    }
                }
            }
        }
        if (phase == 0 )
        {
            commSecondStage.allocate_buffers();
        }
        else
        {
            commSecondStage.communicate();
        }
    }

    for (int proc_that_sent_message=0;proc_that_sent_message<bulk.parallel_size();++proc_that_sent_message)
    {
        if ( proc_that_sent_message == bulk.parallel_rank() ) continue;
        while(commSecondStage.recv_buffer(proc_that_sent_message).remaining())
        {
            stk::mesh::EntityKey key;
            int sharingProc;
            commSecondStage.recv_buffer(proc_that_sent_message).unpack<int>(sharingProc).unpack<stk::mesh::EntityKey>(key);
            if ( sharingProc != bulk.parallel_rank() )
            {
                stk::mesh::Entity entity = bulk.get_entity(key);
                if ( bulk.state(entity) != stk::mesh::Deleted && bulk.is_valid(entity) && !bulk.in_shared(key, sharingProc) )
                {
                    bulk.add_node_sharing(entity, sharingProc);
                }
            }
        }
    }
}