00001
00002
00003
00004
00005
00006
00007 #ifndef AMROC_PROBLEM_H
00008 #define AMROC_PROBLEM_H
00009
00010 #include <cmath>
00011 #include "euler3.h"
00012 #include "ClpProblem.h"
00013
00014 #define f_combl_read FORTRAN_NAME(cblread, CBLREAD)
00015
00016 extern "C" {
00017 void f_combl_read(INTEGER& NSph, DOUBLE xm[], DOUBLE rd[], INTEGER Np[]);
00018 }
00019
00020 #define OWN_GFMAMRSOLVER
00021 #include "ClpStdGFMProblem.h"
00022 #include "AMRGFMInterpolation.h"
00023
00024 class SolverSpecific :
00025 public AMRGFMSolver<VectorType,FixupType,FlagType,DIM> {
00026 typedef VectorType::InternalDataType DataType;
00027 typedef AMRGFMSolver<VectorType,FixupType,FlagType,DIM> base;
00028 typedef AMRGFMInterpolation<VectorType,FixupType,FlagType,DIM> interpolation_type;
00029 typedef interpolation_type::point_type point_type;
00030 typedef F77GFMFileOutput<VectorType,FixupType,FlagType,DIM> output_type;
00031 public:
00032 SolverSpecific(IntegratorSpecific& integ,
00033 base::initial_condition_type& init,
00034 base::boundary_conditions_type& bc) : base(integ, init, bc), OutputDragEvery(1) {
00035 SetLevelTransfer(new F77LevelTransfer<VectorType,DIM>(f_prolong, f_restrict));
00036 #ifdef f_flgout
00037 SetFileOutput(new F77GFMFileOutput<VectorType,FixupType,FlagType,DIM>(*this,f_flgout));
00038 #else
00039 SetFileOutput(new GFMFileOutput<VectorType,FixupType,FlagType,DIM>(*this));
00040 #endif
00041 SetFixup(new FixupSpecific(integ));
00042 SetFlagging(new FlaggingSpecific(*this));
00043 AddGFM(new GhostFluidMethod<VectorType,DIM>(
00044 new F77GFMBoundary<VectorType,DIM>(f_ibndrfl,f_itrans),
00045 new F77GFMLevelSet<DataType,DIM>(f_lset)));
00046 _Interpolation = new interpolation_type(*this);
00047 }
00048
00049 ~SolverSpecific() {
00050 DeleteGFM(_GFM[0]);
00051 delete _Flagging;
00052 delete _Fixup;
00053 delete _Interpolation;
00054 }
00055
00056 virtual void register_at(ControlDevice& Ctrl, const std::string& prefix) {
00057 base::register_at(Ctrl,prefix);
00058 RegisterAt(base::LocCtrl,"OutputDragEvery",OutputDragEvery);
00059 }
00060 virtual void register_at(ControlDevice& Ctrl) {
00061 base::register_at(Ctrl);
00062 }
00063
00064 virtual void SetupData() {
00065 base::SetupData();
00066 _Interpolation->SetupData(base::PGH(), base::NGhosts());
00067 if (OutputDragEvery<=0) OutputDragEvery=1;
00068 }
00069
00070
00071
00072
00073 virtual double Tick(int VariableTimeStepping, const double dtv[],
00074 const double cflv[], int& Rejections) {
00075
00076 double cfl = base::Tick(VariableTimeStepping, dtv, cflv, Rejections);
00077
00078 int TimeZero = CurrentTime(base::GH(),0);
00079 TimeZero /= RefinedBy(base::GH(),MaxLevel(base::GH()));
00080 if (TimeZero % OutputDragEvery != 0) return cfl;
00081
00082 int me = MY_PROC;
00083 double pi = 4.0*std::atan(1.0);
00084
00085
00086 int NSph, Np[5];
00087 double xm[15], rd[5];
00088 point_type sum[5];
00089 f_combl_read(NSph,xm,rd,Np);
00090
00091
00092 for (register int l=0; l<=FineLevel(base::GH()); l++) {
00093 int Time = CurrentTime(base::GH(),l);
00094 int press_cnt = base::Dim()+4;
00095 ((output_type*) _FileOutput)->Transform(base::U(), base::Work(), Time, l,
00096 press_cnt, base::t[l]);
00097 }
00098
00099 for (int ns=0; ns<NSph; ns++) {
00100 int Npoints = 8*Np[ns]*Np[ns];
00101 DataType* p = new DataType[Npoints];
00102 point_type* xc = new point_type[Npoints];
00103 point_type* normals = new point_type[Npoints];
00104 DataType* ds = new DataType[Npoints];
00105 DataType* dist = (DataType*) 0;
00106 double dalpha = 0.5*pi/Np[ns];
00107 double dbeta = 0.5*pi/Np[ns];
00108 register int n = 0;
00109
00110
00111 for (register int l=0; l<4*Np[ns]; l++) {
00112 double alpha = dalpha*(l+0.5);
00113 for (register int m=0; m<2*Np[ns]; m++) {
00114 double beta = dalpha*(m+0.5);
00115 xc[n](0) = xm[base::Dim()*ns ]+rd[ns]*std::cos(alpha)*std::sin(beta);
00116 xc[n](1) = xm[base::Dim()*ns+1]+rd[ns]*std::sin(alpha)*std::sin(beta);
00117 xc[n](2) = xm[base::Dim()*ns+2]+rd[ns]*std::cos(beta);
00118 ds[n] = pi*rd[ns]*rd[ns]*dbeta*std::sin(beta)/(2.*Np[ns]);
00119 n++;
00120 }
00121 }
00122
00123
00124 _Interpolation->PointsValues(base::Work(),base::t[0],Npoints,xc,p);
00125 _Interpolation->ArrayCombine(VizServer,Npoints,p);
00126
00127
00128 _Interpolation->PointsGeom(base::GFM(0).Phi(),base::t[0],Npoints,xc,normals,dist);
00129 _Interpolation->ArrayCombine(VizServer,base::Dim()*Npoints,normals[0].data());
00130
00131
00132 if (me == VizServer) {
00133 sum[ns] = 0.0;
00134 for (n=0; n<Npoints; n++)
00135 sum[ns] += p[n]*normals[n]*ds[n];
00136 }
00137
00138 delete [] p;
00139 delete [] xc;
00140 delete [] normals;
00141 delete [] ds;
00142 }
00143
00144
00145 if (me == VizServer) {
00146 std::ofstream outfile;
00147 std::ostream* out;
00148 std::string fname = "drag.dat";
00149 outfile.open(fname.c_str(), std::ios::out | std::ios::app);
00150 out = new std::ostream(outfile.rdbuf());
00151 *out << base::t[0];
00152 for (int ns=0; ns<NSph; ns++)
00153 for (int d=0; d<base::Dim(); d++)
00154 *out << " " << sum[ns](d);
00155 *out << std::endl;
00156 outfile.close();
00157 delete out;
00158 }
00159
00160 return cfl;
00161 }
00162
00163 protected:
00164 int OutputDragEvery;
00165 interpolation_type* _Interpolation;