void LocationIndexRobinBcCoefs::setBcCoefs( const std::shared_ptr<pdat::ArrayData<double> >& acoef_data, const std::shared_ptr<pdat::ArrayData<double> >& bcoef_data, const std::shared_ptr<pdat::ArrayData<double> >& gcoef_data, const std::shared_ptr<hier::Variable>& variable, const hier::Patch& patch, const hier::BoundaryBox& bdry_box, double fill_time) const { TBOX_ASSERT_DIM_OBJDIM_EQUALITY2(d_dim, patch, bdry_box); NULL_USE(variable); NULL_USE(patch); NULL_USE(fill_time); int location = bdry_box.getLocationIndex(); TBOX_ASSERT(location >= 0 && location < 2 * d_dim.getValue()); if (acoef_data) { TBOX_ASSERT_DIM_OBJDIM_EQUALITY1(d_dim, *acoef_data); acoef_data->fill(d_a_map[location]); } if (bcoef_data) { TBOX_ASSERT_DIM_OBJDIM_EQUALITY1(d_dim, *bcoef_data); bcoef_data->fill(d_b_map[location]); } if (gcoef_data) { TBOX_ASSERT_DIM_OBJDIM_EQUALITY1(d_dim, *gcoef_data); gcoef_data->fill(d_g_map[location]); } }
void EdgeMultiblockTest::fillSingularityBoundaryConditions( hier::Patch& patch, const hier::PatchLevel& encon_level, std::shared_ptr<const hier::Connector> dst_to_encon, const hier::Box& fill_box, const hier::BoundaryBox& bbox, const std::shared_ptr<hier::BaseGridGeometry>& grid_geometry) { const tbox::Dimension& dim = fill_box.getDim(); const hier::BoxId& dst_mb_id = patch.getBox().getBoxId(); const hier::BlockId& patch_blk_id = patch.getBox().getBlockId(); for (int i = 0; i < static_cast<int>(d_variables.size()); ++i) { std::shared_ptr<pdat::EdgeData<double> > edge_data( SAMRAI_SHARED_PTR_CAST<pdat::EdgeData<double>, hier::PatchData>( patch.getPatchData(d_variables[i], getDataContext()))); TBOX_ASSERT(edge_data); hier::Box sing_fill_box(edge_data->getGhostBox() * fill_box); int depth = edge_data->getDepth(); for (int axis = 0; axis < d_dim.getValue(); ++axis) { hier::Box pbox = pdat::EdgeGeometry::toEdgeBox(patch.getBox(), axis); hier::Index plower(pbox.lower()); hier::Index pupper(pbox.upper()); pdat::EdgeIterator niend(pdat::EdgeGeometry::end(sing_fill_box, axis)); for (pdat::EdgeIterator ni(pdat::EdgeGeometry::begin(sing_fill_box, axis)); ni != niend; ++ni) { bool use_index = true; for (tbox::Dimension::dir_t n = 0; n < d_dim.getValue(); ++n) { if (axis != n && bbox.getBox().numberCells(n) == 1) { if ((*ni)(n) == plower(n) || (*ni)(n) == pupper(n)) { use_index = false; break; } } } if (use_index) { for (int d = 0; d < depth; ++d) { (*edge_data)(*ni, d) = 0.0; } } } } int num_encon_used = 0; if (grid_geometry->hasEnhancedConnectivity()) { hier::Connector::ConstNeighborhoodIterator ni = dst_to_encon->findLocal(dst_mb_id); if (ni != dst_to_encon->end()) { for (hier::Connector::ConstNeighborIterator ei = dst_to_encon->begin(ni); ei != dst_to_encon->end(ni); ++ei) { const hier::BlockId& encon_blk_id = ei->getBlockId(); std::shared_ptr<hier::Patch> encon_patch( encon_level.getPatch(ei->getBoxId())); hier::Transformation::RotationIdentifier rotation = hier::Transformation::NO_ROTATE; hier::IntVector offset(dim); hier::BaseGridGeometry::ConstNeighborIterator itr = grid_geometry->find(patch_blk_id, encon_blk_id); if (itr != grid_geometry->end(patch_blk_id)) { rotation = (*itr).getRotationIdentifier(); offset = (*itr).getShift(encon_level.getLevelNumber()); } hier::Transformation transformation(rotation, offset, encon_blk_id, patch_blk_id); hier::Box encon_patch_box(encon_patch->getBox()); transformation.transform(encon_patch_box); hier::Box encon_fill_box(encon_patch_box * sing_fill_box); if (!encon_fill_box.empty()) { const hier::Transformation::RotationIdentifier back_rotate = hier::Transformation::getReverseRotationIdentifier( rotation, dim); hier::IntVector back_shift(dim); hier::Transformation::calculateReverseShift( back_shift, offset, rotation); hier::Transformation back_trans(back_rotate, back_shift, patch_blk_id, encon_blk_id); std::shared_ptr<pdat::EdgeData<double> > sing_data( SAMRAI_SHARED_PTR_CAST<pdat::EdgeData<double>, hier::PatchData>( encon_patch->getPatchData( d_variables[i], getDataContext()))); TBOX_ASSERT(sing_data); for (int axis = 0; axis < d_dim.getValue(); ++axis) { hier::Box pbox( pdat::EdgeGeometry::toEdgeBox(patch.getBox(), axis)); hier::Index plower(pbox.lower()); hier::Index pupper(pbox.upper()); pdat::EdgeIterator ciend(pdat::EdgeGeometry::end(sing_fill_box, axis)); for (pdat::EdgeIterator ci(pdat::EdgeGeometry::begin(sing_fill_box, axis)); ci != ciend; ++ci) { bool use_index = true; for (tbox::Dimension::dir_t n = 0; n < d_dim.getValue(); ++n) { if (axis != n && bbox.getBox().numberCells(n) == 1) { if ((*ci)(n) == plower(n) || (*ci)(n) == pupper(n)) { use_index = false; break; } } } if (use_index) { pdat::EdgeIndex src_index(*ci); pdat::EdgeGeometry::transform(src_index, back_trans); for (int d = 0; d < depth; ++d) { (*edge_data)(*ci, d) += (*sing_data)(src_index, d); } } } } ++num_encon_used; } } } } if (num_encon_used) { for (int axis = 0; axis < d_dim.getValue(); ++axis) { hier::Box pbox = pdat::EdgeGeometry::toEdgeBox(patch.getBox(), axis); hier::Index plower(pbox.lower()); hier::Index pupper(pbox.upper()); pdat::EdgeIterator ciend(pdat::EdgeGeometry::end(sing_fill_box, axis)); for (pdat::EdgeIterator ci(pdat::EdgeGeometry::begin(sing_fill_box, axis)); ci != ciend; ++ci) { bool use_index = true; for (tbox::Dimension::dir_t n = 0; n < d_dim.getValue(); ++n) { if (axis != n && bbox.getBox().numberCells(n) == 1) { if ((*ci)(n) == plower(n) || (*ci)(n) == pupper(n)) { use_index = false; break; } } } if (use_index) { for (int d = 0; d < depth; ++d) { (*edge_data)(*ci, d) /= num_encon_used; } } } } } else { /* * In cases of reduced connectivity, there are no other blocks * from which to acquire data. */ for (int axis = 0; axis < d_dim.getValue(); ++axis) { hier::Box pbox = pdat::EdgeGeometry::toEdgeBox(patch.getBox(), axis); hier::Index plower(pbox.lower()); hier::Index pupper(pbox.upper()); pdat::EdgeIterator ciend(pdat::EdgeGeometry::end(sing_fill_box, axis)); for (pdat::EdgeIterator ci(pdat::EdgeGeometry::begin(sing_fill_box, axis)); ci != ciend; ++ci) { bool use_index = true; for (tbox::Dimension::dir_t n = 0; n < d_dim.getValue(); ++n) { if (axis != n && bbox.getBox().numberCells(n) == 1) { if ((*ci)(n) == plower(n) || (*ci)(n) == pupper(n)) { use_index = false; break; } } } if (use_index) { for (int d = 0; d < depth; ++d) { (*edge_data)(*ci, d) = (double)bbox.getLocationIndex() + 200.0; } } } } } } }
void PoissonGaussianSolution::setBcCoefs( const boost::shared_ptr<pdat::ArrayData<double> >& acoef_data, const boost::shared_ptr<pdat::ArrayData<double> >& bcoef_data, const boost::shared_ptr<pdat::ArrayData<double> >& gcoef_data, const boost::shared_ptr<hier::Variable>& variable, const hier::Patch& patch, const hier::BoundaryBox& bdry_box, const double fill_time) const { NULL_USE(variable); NULL_USE(fill_time); boost::shared_ptr<geom::CartesianPatchGeometry> patch_geom( BOOST_CAST<geom::CartesianPatchGeometry, hier::PatchGeometry>( patch.getPatchGeometry())); TBOX_ASSERT(patch_geom); /* * Set to an inhomogeneous Dirichlet boundary condition. */ hier::Box patch_box(patch.getBox()); const double* xlo = patch_geom->getXLower(); const double* xup = patch_geom->getXUpper(); const double* dx = patch_geom->getDx(); if (bdry_box.getBoundaryType() != 1) { // Must be a face boundary. TBOX_ERROR("Bad boundary type in\n" << "PoissonGaussianSolution::setBcCoefs \n"); } const hier::Box& box = bdry_box.getBox(); hier::Index lower = box.lower(); hier::Index upper = box.upper(); if (d_dim == tbox::Dimension(2)) { double* a_array = acoef_data ? acoef_data->getPointer() : 0; double* b_array = bcoef_data ? bcoef_data->getPointer() : 0; double* g_array = gcoef_data ? gcoef_data->getPointer() : 0; int i, j, ibeg, iend, jbeg, jend; double x, y; switch (bdry_box.getLocationIndex()) { case 0: // min i edge jbeg = box.lower()[1]; jend = box.upper()[1]; x = xlo[0]; for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); if (a_array) a_array[j - jbeg] = 1.0; if (b_array) b_array[j - jbeg] = 0.0; if (g_array) g_array[j - jbeg] = exactFcn(x, y); } break; case 1: // max i edge jbeg = box.lower()[1]; jend = box.upper()[1]; x = xup[0]; for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); if (a_array) a_array[j - jbeg] = 1.0; if (b_array) b_array[j - jbeg] = 0.0; if (g_array) g_array[j - jbeg] = exactFcn(x, y); } break; case 2: // min j edge ibeg = box.lower()[0]; iend = box.upper()[0]; y = xlo[1]; for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array[i - ibeg] = 1.0; if (b_array) b_array[i - ibeg] = 0.0; if (g_array) g_array[i - ibeg] = exactFcn(x, y); } break; case 3: // max j edge ibeg = box.lower()[0]; iend = box.upper()[0]; y = xup[1]; for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array[i - ibeg] = 1.0; if (b_array) b_array[i - ibeg] = 0.0; if (g_array) g_array[i - ibeg] = exactFcn(x, y); } break; default: TBOX_ERROR("Invalid location index in\n" << "PoissonGaussianSolution::setBcCoefs"); } } if (d_dim == tbox::Dimension(3)) { MDA_Access<double, 3, MDA_OrderColMajor<3> > a_array, b_array, g_array; if (acoef_data) a_array = pdat::ArrayDataAccess::access<3, double>( *acoef_data); if (bcoef_data) b_array = pdat::ArrayDataAccess::access<3, double>( *bcoef_data); if (gcoef_data) g_array = pdat::ArrayDataAccess::access<3, double>( *gcoef_data); int i, j, k, ibeg, iend, jbeg, jend, kbeg, kend; double x, y, z; switch (bdry_box.getLocationIndex()) { case 0: // min i side jbeg = box.lower()[1]; jend = box.upper()[1]; kbeg = box.lower()[2]; kend = box.upper()[2]; i = box.lower()[0] + 1; x = xlo[0]; for (k = kbeg; k <= kend; ++k) { z = xlo[2] + dx[2] * (k - patch_box.lower()[2] + 0.5); for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; case 1: // max i side jbeg = box.lower()[1]; jend = box.upper()[1]; kbeg = box.lower()[2]; kend = box.upper()[2]; i = box.upper()[0]; x = xup[0]; for (k = kbeg; k <= kend; ++k) { z = xlo[2] + dx[2] * (k - patch_box.lower()[2] + 0.5); for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; case 2: // min j side ibeg = box.lower()[0]; iend = box.upper()[0]; kbeg = box.lower()[2]; kend = box.upper()[2]; j = box.lower()[1] + 1; y = xlo[1]; for (k = kbeg; k <= kend; ++k) { z = xlo[2] + dx[2] * (k - patch_box.lower()[2] + 0.5); for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; case 3: // max j side ibeg = box.lower()[0]; iend = box.upper()[0]; kbeg = box.lower()[2]; kend = box.upper()[2]; j = box.upper()[1]; y = xup[1]; for (k = kbeg; k <= kend; ++k) { z = xlo[2] + dx[2] * (k - patch_box.lower()[2] + 0.5); for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; case 4: // min k side ibeg = box.lower()[0]; iend = box.upper()[0]; jbeg = box.lower()[1]; jend = box.upper()[1]; k = box.lower()[2] + 1; z = xlo[2]; for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; case 5: // max k side ibeg = box.lower()[0]; iend = box.upper()[0]; jbeg = box.lower()[1]; jend = box.upper()[1]; k = box.upper()[2]; z = xup[2]; for (j = jbeg; j <= jend; ++j) { y = xlo[1] + dx[1] * (j - patch_box.lower()[1] + 0.5); for (i = ibeg; i <= iend; ++i) { x = xlo[0] + dx[0] * (i - patch_box.lower()[0] + 0.5); if (a_array) a_array(i, j, k) = 1.0; if (b_array) b_array(i, j, k) = 0.0; if (g_array) g_array(i, j, k) = exactFcn(x, y, z); } } break; default: TBOX_ERROR("Invalid location index in\n" << "PoissonGaussianSolution::setBcCoefs"); } } }
int SkeletonBoundaryUtilities2::checkBdryData( const string& varname, const hier::Patch& patch, int data_id, int depth, const hier::IntVector& gcw_to_check, const hier::BoundaryBox& bbox, int bcase, double bstate) { TBOX_ASSERT(!varname.empty()); TBOX_ASSERT(data_id >= 0); TBOX_ASSERT(depth >= 0); int num_bad_values = 0; int btype = bbox.getBoundaryType(); int bloc = bbox.getLocationIndex(); std::shared_ptr<hier::PatchGeometry> pgeom(patch.getPatchGeometry()); std::shared_ptr<pdat::CellData<double> > vardata( SAMRAI_SHARED_PTR_CAST<pdat::CellData<double>, hier::PatchData>( patch.getPatchData(data_id))); TBOX_ASSERT(vardata); string bdry_type_str; if (btype == Bdry::EDGE2D) { bdry_type_str = "EDGE"; } else if (btype == Bdry::NODE2D) { bdry_type_str = "NODE"; } else { TBOX_ERROR( "Unknown btype " << btype << " passed to SkeletonBoundaryUtilities2::checkBdryData()! " << endl); } tbox::plog << "\n\nCHECKING 2D " << bdry_type_str << " BDRY DATA..." << endl; tbox::plog << "varname = " << varname << " : depth = " << depth << endl; tbox::plog << "bbox = " << bbox.getBox() << endl; tbox::plog << "btype, bloc, bcase = " << btype << ", = " << bloc << ", = " << bcase << endl; tbox::Dimension::dir_t idir; double valfact = 0.0, constval = 0.0, dxfact = 0.0; int offsign; get2dBdryDirectionCheckValues(idir, offsign, btype, bloc, bcase); if (btype == Bdry::EDGE2D) { if (bcase == BdryCond::FLOW) { valfact = 1.0; constval = 0.0; dxfact = 0.0; } else if (bcase == BdryCond::REFLECT) { valfact = -1.0; constval = 0.0; dxfact = 0.0; } else if (bcase == BdryCond::DIRICHLET) { valfact = 0.0; constval = bstate; dxfact = 0.0; } else { TBOX_ERROR( "Unknown bcase " << bcase << " passed to SkeletonBoundaryUtilities2::checkBdryData()" << "\n for " << bdry_type_str << " at location " << bloc << endl); } } else if (btype == Bdry::NODE2D) { if (bcase == BdryCond::XFLOW || bcase == BdryCond::YFLOW) { valfact = 1.0; constval = 0.0; dxfact = 0.0; } else if (bcase == BdryCond::XREFLECT || bcase == BdryCond::YREFLECT) { valfact = -1.0; constval = 0.0; dxfact = 0.0; } else if (bcase == BdryCond::XDIRICHLET || bcase == BdryCond::YDIRICHLET) { valfact = 0.0; constval = bstate; dxfact = 0.0; } else { TBOX_ERROR( "Unknown bcase " << bcase << " passed to SkeletonBoundaryUtilities2::checkBdryData()" << "\n for " << bdry_type_str << " at location " << bloc << endl); } } hier::Box gbox_to_check( vardata->getGhostBox() * pgeom->getBoundaryFillBox(bbox, patch.getBox(), gcw_to_check)); hier::Box cbox(gbox_to_check); hier::Box dbox(gbox_to_check); hier::Index ifirst(vardata->getBox().lower()); hier::Index ilast(vardata->getBox().upper()); if (offsign == -1) { cbox.setLower(idir, ifirst(idir) - 1); cbox.setUpper(idir, ifirst(idir) - 1); dbox.setLower(idir, ifirst(idir)); dbox.setUpper(idir, ifirst(idir)); } else { cbox.setLower(idir, ilast(idir) + 1); cbox.setUpper(idir, ilast(idir) + 1); dbox.setLower(idir, ilast(idir)); dbox.setUpper(idir, ilast(idir)); } pdat::CellIterator id(pdat::CellGeometry::begin(dbox)); pdat::CellIterator icend(pdat::CellGeometry::end(cbox)); for (pdat::CellIterator ic(pdat::CellGeometry::begin(cbox)); ic != icend; ++ic) { double checkval = valfact * (*vardata)(*id, depth) + constval; pdat::CellIndex check = *ic; for (int p = 0; p < gbox_to_check.numberCells(idir); ++p) { double offcheckval = checkval + dxfact * (p + 1); if ((*vardata)(check, depth) != offcheckval) { ++num_bad_values; TBOX_WARNING("Bad " << bdry_type_str << " boundary value for " << varname << " found in cell " << check << "\n found = " << (*vardata)(check, depth) << " : correct = " << offcheckval << endl); } check(idir) += offsign; } ++id; } return num_bad_values; }