Beispiel #1
0
void pml_txx(float **txxn1, float **vxn1, float **vzn1, float **c11, 
	     float (*ldx)(float **, int, int), 
	     float (*ldz)(float **, int, int),
             bool freesurface )
/*<stress decay in pml>*/
{
    int ix, iz;
    /*Stress PML -- top*/
    if (freesurface == false) {
	for (ix=marg; ix<nx+2*pmlout+marg; ix++) {
	    for (iz=marg; iz<marg+pmlout; iz++) {
		txxn1x[ix][iz]=((1-dt*pmldx[ix]/2)*txxn0x[ix][iz]-dt*c11[ix][iz]*ldx(vxn1,ix-1,iz))/(1+dt*pmldx[ix]/2);
		txxn1z[ix][iz]=((1-dt*pmldz[iz]/2)*txxn0z[ix][iz]-dt*c11[ix][iz]*ldz(vzn1,ix,iz-1))/(1+dt*pmldz[iz]/2);
		txxn1[ix][iz] = txxn1x[ix][iz]+txxn1z[ix][iz];
	    }
	}
    } else {
	for (ix=marg; ix<nx+2*pmlout+marg; ix++) {
	    for (iz=marg; iz<marg+pmlout; iz++) {
		txxn1x[ix][iz]=((1-dt*pmldx[ix]/2)*txxn0x[ix][iz]-dt*0.0*ldx(vxn1,ix-1,iz))/(1+dt*pmldx[ix]/2);
		txxn1z[ix][iz]=((1-dt*pmldz[iz]/2)*txxn0z[ix][iz]-dt*0.0*ldz(vzn1,ix,iz-1))/(1+dt*pmldz[iz]/2);
		txxn1[ix][iz] = txxn1x[ix][iz]+txxn1z[ix][iz];
	    }
	}
    }

    /*Stress PML -- left*/
    for (ix=marg; ix<marg+pmlout; ix++) {
	for (iz=marg+pmlout; iz<nz+pmlout+marg; iz++) {
	    txxn1x[ix][iz]=((1-dt*pmldx[ix]/2)*txxn0x[ix][iz]-dt*c11[ix][iz]*ldx(vxn1,ix-1,iz))/(1+dt*pmldx[ix]/2);
	    txxn1z[ix][iz]=((1-dt*pmldz[iz]/2)*txxn0z[ix][iz]-dt*c11[ix][iz]*ldz(vzn1,ix,iz-1))/(1+dt*pmldz[iz]/2);
	    txxn1[ix][iz] = txxn1x[ix][iz]+txxn1z[ix][iz];
	}
    }
    /*Stress PML -- right*/
    for (ix=nx+pmlout+marg; ix<nx+2*pmlout+marg; ix++) {
	for (iz=marg+pmlout; iz<nz+pmlout+marg; iz++) {
	    txxn1x[ix][iz]=((1-dt*pmldx[ix]/2)*txxn0x[ix][iz]-dt*c11[ix][iz]*ldx(vxn1,ix-1,iz))/(1+dt*pmldx[ix]/2);
	    txxn1z[ix][iz]=((1-dt*pmldz[iz]/2)*txxn0z[ix][iz]-dt*c11[ix][iz]*ldz(vzn1,ix,iz-1))/(1+dt*pmldz[iz]/2);
	    txxn1[ix][iz] = txxn1x[ix][iz]+txxn1z[ix][iz];
	}
    }
    /*Stress PML -- bottom*/
    for (ix=marg; ix<nx+2*pmlout+marg; ix++) {
	for (iz=marg+pmlout+nz; iz<nz+2*pmlout+marg; iz++) {
	    txxn1x[ix][iz]=((1-dt*pmldx[ix]/2)*txxn0x[ix][iz]-dt*c11[ix][iz]*ldx(vxn1,ix-1,iz))/(1+dt*pmldx[ix]/2);
	    txxn1z[ix][iz]=((1-dt*pmldz[iz]/2)*txxn0z[ix][iz]-dt*c11[ix][iz]*ldz(vzn1,ix,iz-1))/(1+dt*pmldz[iz]/2);
	    txxn1[ix][iz] = txxn1x[ix][iz]+txxn1z[ix][iz];
	}
    }	
}
Beispiel #2
0
void pml_vxz(float **vxn1, float **vzn1, float **vxn0, float **vzn0, 
	     float **txxn0, float **denx, float **denz,
	     float (*ldx)(float **, int, int), 
	     float (*ldz)(float **, int, int),
             bool freesurface)
/*<velocity vx,vz  decay in pml>*/
{
    int ix, iz;
    /*Velocity PML --top*/
    if (freesurface == false) {
	for (ix=marg; ix<nx+2*pmlout+marg; ix++) {
	    for (iz=marg; iz<marg+pmlout; iz++) {
		vxn1[ix][iz]=((1-dt*pmldx[ix]/2)*vxn0[ix][iz]-dt/denx[ix][iz]*ldx(txxn0,ix,iz))/(1+dt*pmldx[ix]/2);
		vzn1[ix][iz]=((1-dt*pmldz[iz]/2)*vzn0[ix][iz]-dt/denz[ix][iz]*ldz(txxn0,ix,iz))/(1+dt*pmldz[iz]/2);
	    }
	}
    } 
	
    /*Velocity PML  --left*/
    for (ix=marg; ix<marg+pmlout; ix++) {
	for (iz=marg+pmlout; iz<nz+pmlout+marg; iz++) {
	    vxn1[ix][iz]=((1-dt*pmldx[ix]/2)*vxn0[ix][iz]-dt/denx[ix][iz]*ldx(txxn0,ix,iz))/(1+dt*pmldx[ix]/2);
	    vzn1[ix][iz]=((1-dt*pmldz[iz]/2)*vzn0[ix][iz]-dt/denz[ix][iz]*ldz(txxn0,ix,iz))/(1+dt*pmldz[iz]/2);
	}
    }
    /*Velocity PML  --right*/
    for (ix=nx+pmlout+marg; ix<nx+2*pmlout+marg; ix++) {
	for (iz=marg+pmlout; iz<nz+pmlout+marg; iz++) {
	    vxn1[ix][iz]=((1-dt*pmldx[ix]/2)*vxn0[ix][iz]-dt/denx[ix][iz]*ldx(txxn0,ix,iz))/(1+dt*pmldx[ix]/2);
	    vzn1[ix][iz]=((1-dt*pmldz[iz]/2)*vzn0[ix][iz]-dt/denz[ix][iz]*ldz(txxn0,ix,iz))/(1+dt*pmldz[iz]/2);
	}
    }
    /*Velocity PML  --bottom*/
    for (ix=marg; ix<nx+2*pmlout+marg; ix++) {
	for (iz=marg+pmlout+nz; iz<nz+2*pmlout+marg; iz++) {
	    vxn1[ix][iz]=((1-dt*pmldx[ix]/2)*vxn0[ix][iz]-dt/denx[ix][iz]*ldx(txxn0,ix,iz))/(1+dt*pmldx[ix]/2);
	    vzn1[ix][iz]=((1-dt*pmldz[iz]/2)*vzn0[ix][iz]-dt/denz[ix][iz]*ldz(txxn0,ix,iz))/(1+dt*pmldz[iz]/2);
	}
    }
}
Beispiel #3
0
int sglfdback2(float ***mig1, float **mig2, float ***fwf, float **localrec, bool verb, bool wantwf, sf_file Ftmpbwf)
{
	float **txxn1, **txxn0, **vxn1, **vxn0, **vzn1, **vzn0;
	float **sill, **ccr, ***bwf;
	int wfit, htau;
	float tau;

	sill=sf_floatalloc2(nz, nx);
	ccr=sf_floatalloc2(nz, nx);
	bwf=sf_floatalloc3(nz, nx, wfnt);
	zero2(sill, nz, nx);
	zero2(ccr, nz, nx);
	zero3(mig1, nz, nx, ntau);

	txxn1=sf_floatalloc2(nzb, nxb);
	txxn0=sf_floatalloc2(nzb, nxb);
	vxn1=sf_floatalloc2(nzb, nxb);
	vxn0=sf_floatalloc2(nzb, nxb);
	vzn1=sf_floatalloc2(nzb, nxb);
	vzn0=sf_floatalloc2(nzb, nxb);

	zero2(txxn1, nzb, nxb);
	zero2(txxn0, nzb, nxb);
	zero2(vxn1, nzb, nxb);
	zero2(vxn0, nzb, nxb);
	zero2(vzn1, nzb, nxb);
	zero2(vzn0, nzb, nxb);

	zero2(txxn1x, nzb, nxb);
	zero2(txxn1z, nzb, nxb);
	zero2(txxn0x, nzb, nxb);
	zero2(txxn0z, nzb, nxb);
	
	wfit=wfnt-1;
	for(it=nt-1; it>=0; it--){
		if(verb) sf_warning("Backward it=%d/%d;", it+1, nt);
#ifdef _OPENMP
#pragma omp parallel for private(ix,iz)
#endif
		for(ix=nfd+pmlsize; ix<nfd+pmlsize+nx; ix++){
			for(iz=nfd+pmlsize; iz<nfd+pmlsize+nz; iz++){
				txxn0[ix][iz]=txxn1[ix][iz]+dt*bc11[ix][iz]*(ldx(vxn1, ix-1, iz) +ldz(vzn1, ix, iz-1));
			}
		}

		pml_txxb(txxn0, vxn1, vzn1);
#ifdef _OPENMP
#pragma omp parallel for private(ix)
#endif
		for(ix=0; ix<ng; ix++){
			txxn0[ix*ginv+pmlsize+nfd][pmlsize+nfd+gp]+=localrec[ix][it];
		}
#ifdef _OPENMP
#pragma omp parallel for private(ix,iz)
#endif
		for(ix=nfd+pmlsize; ix<nfd+pmlsize+nx; ix++){
			for(iz=nfd+pmlsize; iz<nfd+pmlsize+nz; iz++){
				vxn0[ix][iz]=vxn1[ix][iz]+dt/bdenx[ix][iz]*ldx(txxn0, ix, iz);
				vzn0[ix][iz]=vzn1[ix][iz]+dt/bdenz[ix][iz]*ldz(txxn0, ix, iz);
			}
		}

		pml_vxzb(vxn1, vzn1, vxn0, vzn0, txxn0);

		transp=txxn1; txxn1=txxn0; txxn0=transp;
		transp=vxn1; vxn1=vxn0; vxn0=transp;
		transp=vzn1; vzn1=vzn0; vzn0=transp;

		if(it%wfinv==0){
			for(ix=0; ix<nx; ix++)
				for(iz=0; iz<nz; iz++){
					bwf[wfit][ix][iz]=txxn0[ix+pmlsize+nfd][iz+pmlsize+nfd];
					ccr[ix][iz]+=fwf[wfit][ix][iz]*bwf[wfit][ix][iz];
					sill[ix][iz]+=fwf[wfit][ix][iz]*fwf[wfit][ix][iz];
				}
			wfit--;
		}
	} //end of it
	if(verb) sf_warning(".");

	for(itau=0; itau<ntau; itau++){
		tau=itau*dtau+tau0;
		htau=tau/wfdt;
		for(it=abs(htau); it<wfnt-abs(htau); it++){
			for(ix=0; ix<nx; ix++){
				for(iz=0; iz<nz; iz++){
					mig1[itau][ix][iz]+=fwf[it+htau][ix][iz]*bwf[it-htau][ix][iz];
				}
			}
		}//end of it
	} // end of itau

	for(ix=0; ix<nx; ix++){
		for(iz=0; iz<nz; iz++){
			mig2[ix][iz]=ccr[ix][iz]/(sill[ix][iz]+SF_EPS);
		}
	}

	if(wantwf) sf_floatwrite(bwf[0][0], wfnt*nx*nz, Ftmpbwf);
	return 0;
}
Beispiel #4
0
int sglfdfor2(float ***fwf, float **rcd, bool verb)
{
	float **txxn1, **txxn0, **vxn1, **vxn0, **vzn1, **vzn0;
	int wfit;

	txxn1=sf_floatalloc2(nzb, nxb);
	txxn0=sf_floatalloc2(nzb, nxb);
	vxn1=sf_floatalloc2(nzb, nxb);
	vxn0=sf_floatalloc2(nzb, nxb);
	vzn1=sf_floatalloc2(nzb, nxb);
	vzn0=sf_floatalloc2(nzb, nxb);

	zero2(txxn1, nzb, nxb);
	zero2(txxn0, nzb, nxb);
	zero2(vxn1, nzb, nxb);
	zero2(vxn0, nzb, nxb);
	zero2(vzn1, nzb, nxb);
	zero2(vzn0, nzb, nxb);

	zero2(txxn1x, nzb, nxb);
	zero2(txxn1z, nzb, nxb);
	zero2(txxn0x, nzb, nxb);
	zero2(txxn0z, nzb, nxb);

	wfit=0;
	for(it=0; it<nt; it++){
//		sf_warning("test txxn1[801][30]=%d",txxn1[801][30])
		if(verb) sf_warning("Forward it=%d/%d;", it+1, nt);
#ifdef _OPENMP
#pragma omp parallel for private(ix,iz)
#endif
		for(ix=nfd+pmlsize; ix<nfd+pmlsize+nx; ix++){
			for(iz=nfd+pmlsize; iz<nfd+pmlsize+nz; iz++){
				vxn1[ix][iz]=vxn0[ix][iz]-dt/fdenx[ix][iz]*ldx(txxn0, ix, iz);
				vzn1[ix][iz]=vzn0[ix][iz]-dt/fdenz[ix][iz]*ldz(txxn0, ix, iz);
			}
		}

		pml_vxz(vxn1, vzn1, vxn0, vzn0, txxn0);
#ifdef _OPENMP
#pragma omp parallel for private(ix,iz)
#endif
		for(ix=nfd+pmlsize; ix<nfd+pmlsize+nx; ix++){
			for(iz=nfd+pmlsize; iz<nfd+pmlsize+nz; iz++){
				txxn1[ix][iz]=txxn0[ix][iz]-dt*fc11[ix][iz]*(ldx(vxn1, ix-1, iz) + ldz(vzn1, ix, iz-1));
			}
		}

		pml_txx(txxn1, vxn1, vzn1);

		if((it*dt)<srctrunc){
			explsource(txxn1);
		}

		if(it%wfinv==0){
#ifdef _OPENMP
#pragma omp parallel for private(ix,iz)
#endif
			for(ix=0; ix<nx; ix++){
				for(iz=0; iz<nz; iz++){
					fwf[wfit][ix][iz]=txxn0[ix+nfd+pmlsize][iz+nfd+pmlsize];
				}
			}
			wfit++;
		}
#ifdef _OPENMP
#pragma omp parallel for private(ix)
#endif
		for(ix=0; ix<ng; ix++){
			rcd[ix][it]=txxn0[ix*ginv+pmlsize+nfd][pmlsize+nfd+gp];
		}

		transp=txxn0; txxn0=txxn1; txxn1=transp;
		transp=vxn0;  vxn0=vxn1;   vxn1=transp;
		transp=vzn0;  vzn0=vzn1;   vzn1=transp;
	} // end of it
	if(verb) sf_warning(".");
	return 0;;
}
Beispiel #5
0
            void build(const pixmap<T> &source,
                       const size_t     links)
            {
                assert(same_metrics_than(source));
                assert(4==links||8==links);
                _tagmap &self = *this;

                //______________________________________________________________
                //
                // initialize all
                //______________________________________________________________
                current = 0;
                ldz();
                vstk.free();

                for(unit_t j=0;j<h;++j)
                {
                    row                           &tag_j = self[j];
                    const typename pixmap<T>::row &src_j = source[j];
                    for(unit_t i=0;i<w;++i)
                    {
                        size_t &tag = tag_j[i];
                        if(0==tag)
                        {
                            //__________________________________________________
                            //
                            // no current tag
                            //__________________________________________________
                            if(!pixel<T>::is_zero(src_j[i]))
                            {
                                //______________________________________________
                                //
                                // start a new tag !
                                //______________________________________________
                                tag = ++current;

                                //______________________________________________
                                //
                                // initialize stack
                                //______________________________________________
                                vstk.free();
                                {
                                    const vertex here(i,j);
                                    vstk.push(here);
                                }

                                //______________________________________________
                                //
                                // not recursive build
                                //______________________________________________
                                while( vstk.size() > 0 )
                                {
                                    //__________________________________________
                                    //
                                    // remove one vertex from stack
                                    //__________________________________________
                                    const vertex here = vstk.peek();
                                    assert(self[here]==current);
                                    vstk.pop();

                                    //__________________________________________
                                    //
                                    // probe neighbors
                                    //__________________________________________
                                    for(size_t k=0;k<links;++k)
                                    {
                                        const vertex probe = here + gist::delta[k];
                                        if(source.has(probe) && 0==self[probe] && !pixel<T>::is_zero(source[probe]))
                                        {
                                            self[probe]=current;
                                            vstk.push(probe);
                                        }
                                    }
                                }


                            }
                        }
                    }
                }

                vstk.free();
            }
Beispiel #6
0
        void EdgeDetector:: post_build(xpatches &xps)
        {
            edges.free();

            // get the global max
            Gmax = xps[1].as<float>();
            for(size_t i=xps.size();i>1;--i)
            {
                Gmax = max_of(Gmax,xps[i].as<float>());
            }


            if(Gmax>0)
            {
                //! normalize as probability
                xps.submit(this, &EdgeDetector::normalize );

                //! non local maxima suprresion
                xps.submit(this, &EdgeDetector::non_maxima_suppress);

                //! thresholds computation
                H.reset();
                H.update(E,xps);
                level_up = H.threshold();
                const size_t level_min   = level_lo/2;
                const size_t level_delta = size_t( floor( (level_up-level_min) * weak_intake + 0.5f) );
                level_lo = level_up-level_delta;

                //! apply threshold
                xps.submit(this, &EdgeDetector::apply_thresholds);

                //! build blobs
                tags.build(E,8);

                //! find individual edges
                edges.load(tags);


                // removing weak only edges
                pixmap<float> &G = *this;
                for(size_t i=edges.size();i>0;--i)
                {
                    particle &p = *edges[i];
                    assert(p.size>0);
                    assert(p.inside.size<=0);
                    assert(p.border.size<=0);
                    // detect if at least one strong connected edge
                    bool is_strong = false;
                    for(const vnode *node = p.head;node;node=node->next)
                    {
                        if(STRONG==E[node->vtx])
                        {
                            is_strong=true;
                            break;
                        }
                    }

                    // remove it !
                    if(!is_strong)
                    {
                        while(p.size)
                        {
                            vnode       *node = p.pop_back();
                            const vertex q    = node->vtx;

                            tags[q] = 0;
                            E[q]    = 0;
                            G[q]    = 0;

                            delete node;
                        }
                    }
                }
                remove_if(edges,__is_empty_particle);
                //std::cerr << "#edges=" << edges.size() << std::endl;
            }
            else
            {
                ldz();
                E.ldz();
                tags.ldz();
            }

        }
Beispiel #7
0
int sglfdfor2(float ***wavfld, float **rcd, bool verb,
              float **den, float **c11, 
              geopar geop, srcpar srcp, pmlpar pmlp)
/*< staggered grid lowrank FD forward modeling >*/
{
    /*caculate arrays*/
    float **txxn1, **txxn0, **vxn1, **vzn1, **vxn0, **vzn0;

    float **denx, **denz;
    /*grid index*/
    int nx, nz, nt, ix, iz, it;
    int nxb, nzb, snpint;
    int spx, spz, gp,  gn, ginter;
    float dt, dx, dz;
    int pmlout, marg;
    bool freesurface;
    
    /* tmp variable */
    int wfit;
    int nth;

    nx = geop->nx;
    nz = geop->nz;
    nxb = geop->nxb;
    nzb = geop->nzb;
    dx = geop->dx;
    dz = geop->dz;

    spx = geop->spx;
    spz = geop->spz;
    gp  = geop->gp;
    gn  = geop->gn;
    ginter = geop->ginter;

    snpint = geop->snpint;

    nt = srcp->nt;
    dt = srcp->dt;

    pmlout = pmlp->pmlout;
    freesurface = pmlp->freesurface;
    marg   = getmarg();
    

    denx = sf_floatalloc2(nzb, nxb);
    denz = sf_floatalloc2(nzb, nxb);

#ifdef _OPENMP
#pragma omp parallel  
{
    nth = omp_get_num_threads();
}
#endif
 sf_warning(">>>> Using %d threads <<<<<", nth);

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for ( iz= 0; iz < nzb; iz++) {
	    denx[ix][iz] = den[ix][iz];
	    denz[ix][iz] = den[ix][iz];
	}
    }
    /*den[ix+1/2][iz]*/

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for ( ix = 0; ix < nxb-1; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    denx[ix][iz] = (den[ix+1][iz] + den[ix][iz])*0.5;
	}
    }
    /*den[ix][iz+1/2]*/
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for ( ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb-1; iz++) {
	    denz[ix][iz] = (den[ix][iz+1] + den[ix][iz])*0.5;
	}
    }

    txxn1 = sf_floatalloc2(nzb, nxb);
    txxn0 = sf_floatalloc2(nzb, nxb);
    vxn1  = sf_floatalloc2(nzb, nxb);
    vzn1  = sf_floatalloc2(nzb, nxb);
    vxn0  = sf_floatalloc2(nzb, nxb);
    vzn0  = sf_floatalloc2(nzb, nxb);

    init_pml(nz, nx, dt, marg, pmlp);
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    txxn1[ix][iz] = 0.0;
	 }
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    txxn0[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vxn1[ix][iz] = 0.0;  
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vxn0[ix][iz] = 0.0;
	}
    } 
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vzn1[ix][iz] = 0.0;  
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vzn0[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif  
    for (it = 0; it < nt; it++) {
	for (ix = 0; ix < gn; ix++) {
	    rcd[ix][it] = 0.0;
	}
    }  

    /*Main loop*/
    wfit = 0;
    for (it = 0; it < nt; it++) {
	if (verb) sf_warning("Forward it=%d/%d;", it, nt-1);
	
	/*velocity*/
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	for (ix = marg+pmlout; ix < nx+pmlout+marg; ix++ ) {
	    for (iz = marg+pmlout; iz < nz+pmlout+marg; iz++) {
		vxn1[ix][iz] = vxn0[ix][iz] - dt/denx[ix][iz]*ldx(txxn0, ix, iz);
		vzn1[ix][iz] = vzn0[ix][iz] - dt/denz[ix][iz]*ldz(txxn0, ix, iz);
	    }
	}
	
	/*Velocity PML */
	pml_vxz(vxn1, vzn1, vxn0, vzn0, txxn0, denx, denz, ldx, ldz, freesurface);
	
	/*Stress*/
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	for (ix = marg+pmlout; ix < nx+marg+pmlout; ix++) {
	    for ( iz = marg+pmlout; iz < nz+marg+pmlout; iz++) { 
		txxn1[ix][iz] = txxn0[ix][iz] - dt*c11[ix][iz]*(ldx(vxn1, ix-1, iz) + ldz(vzn1, ix, iz-1));
	    }
	}
	 
	/*Stress PML */
	pml_txx(txxn1, vxn1, vzn1, c11, ldx, ldz, freesurface);
	
	if ((it*dt)<=srcp->trunc) {
	    explsourcet(txxn1, srcp->wavelet, it, dt, spx+pmlout+marg, spz+pmlout+marg, nxb, nzb, srcp);
	}
	
	if ( it%snpint == 0 ) {
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	    for ( ix = 0; ix < nx; ix++) 
		for ( iz = 0; iz<nz; iz++ )
		    wavfld[wfit][ix][iz] = txxn0[ix+pmlout+marg][iz+pmlout+marg];
	    wfit++;
	}
	
	//sf_warning("test I am at 257");
	
#ifdef _OPENMP
#pragma omp parallel for private(ix)
#endif	 
	for ( ix =0 ; ix < gn; ix++) {
	    rcd[ix][it] = txxn0[ix*ginter+pmlout+marg][pmlout+marg+gp];
	    //sf_warning("gn=%d ix=%d ginter=%d ix*ginter=%d", gn, ginter, ix, ix*ginter);
	}

	//sf_warning("test I am at 266");
	
	/*n1 -> n0*/
	time_step_exch(txxn0, txxn1, it);
	time_step_exch(vxn0, vxn1, it);
	time_step_exch(vzn0, vzn1, it);
	pml_tstep_exch(it);
	
    } /*Main loop*/
    if (verb) sf_warning(".");
    return wfit;
    
}
Beispiel #8
0
int sglfdback2(float **img1, float **img2, float ***wavfld, float **rcd, 
               bool verb, bool wantwf, float **den, float **c11, 
               geopar geop, srcpar srcp, pmlpar pmlp, sf_file Ftmpbwf)  
/*< staggered grid lowrank FD backward propagation + imaging >*/
{
    /*caculate arrays*/
    float **txxn1, **txxn0, **vxn1, **vzn1, **vxn0, **vzn0;
    
    float **denx, **denz;
    float **sill, **ccr;
    /*grid index*/
    int nx, nz, nt, ix, iz, it, gn, ginter;
    int nxb, nzb, snpint;
    int gp;
    float dt, dx, dz;
    int pmlout, marg;
    bool freesurface;

    /* tmp variable */
    int wfit;
    
    nx = geop->nx;
    nz = geop->nz;
    nxb = geop->nxb;
    nzb = geop->nzb;
    dx = geop->dx;
    dz = geop->dz;
    
    gp  = geop->gp;
    gn  = geop->gn;
    ginter= geop->ginter;
    snpint = geop->snpint;
    
    nt = srcp->nt;
    dt = srcp->dt;

    pmlout = pmlp->pmlout;
    freesurface = pmlp->freesurface;
    marg   = getmarg();

    denx = sf_floatalloc2(nzb, nxb);
    denz = sf_floatalloc2(nzb, nxb);

    sill = sf_floatalloc2(nz, nx);
    ccr  = img1;

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif    
    for (ix = 0; ix < nxb; ix++) {
	for ( iz= 0; iz < nzb; iz++) {
	    denx[ix][iz] = den[ix][iz];
	    denz[ix][iz] = den[ix][iz];
	}
    }
    /*den[ix+1/2][iz]*/

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for ( ix = 0; ix < nxb-1; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    denx[ix][iz] = (den[ix+1][iz] + den[ix][iz])*0.5;
	}
    }
    /*den[ix][iz+1/2]*/

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for ( ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb-1; iz++) {
	    denz[ix][iz] = (den[ix][iz+1] + den[ix][iz])*0.5;
	}
    }
    
    txxn1 = sf_floatalloc2(nzb, nxb);
    txxn0 = sf_floatalloc2(nzb, nxb);
    vxn1  = sf_floatalloc2(nzb, nxb);
    vzn1  = sf_floatalloc2(nzb, nxb);
    vxn0  = sf_floatalloc2(nzb, nxb);
    vzn0  = sf_floatalloc2(nzb, nxb);

    init_pml(nz, nx, dt, marg, pmlp);
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif    
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    txxn1[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    txxn0[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vxn1[ix][iz] = 0.0;  
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vxn0[ix][iz] = 0.0;
	}
    } 
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vzn1[ix][iz] = 0.0;  
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nxb; ix++) {
	for (iz = 0; iz < nzb; iz++) {
	    vzn0[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nx; ix++) {
	for (iz = 0; iz < nz; iz++) {
	    sill[ix][iz] = 0.0;
	}
    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
    for (ix = 0; ix < nx; ix++) {
	for (iz = 0; iz < nz; iz++) {
	    ccr[ix][iz] = 0.0;
	}
    }
        
    /*Main loop*/
    wfit = (int)(nt-1)/snpint;
    
    for (it = nt-1; it>=0; it--) {
	if  (verb) sf_warning("Backward it=%d/%d;", it, nt-1);

	/*Stress*/
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	for (ix = marg+pmlout; ix < nx+marg+pmlout; ix++) {
	    for ( iz = marg+pmlout; iz < nz+marg+pmlout; iz++) { 
		txxn0[ix][iz] = txxn1[ix][iz] + dt*c11[ix][iz]*(ldx(vxn1, ix-1, iz) + ldz(vzn1, ix, iz-1));
	    }
	}
	/*Stress PML */
	pml_txxb(txxn0, vxn1, vzn1, c11, ldx, ldz, freesurface);

#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif	
	for (ix=0; ix<gn; ix++)  {
	    txxn0[ix*ginter+pmlout+marg][pmlout+marg+gp] = rcd[ix][it];
	}
	
	/*velocity*/
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	for (ix = marg+pmlout; ix < nx+pmlout+marg; ix++ ) {
	    for (iz = marg+pmlout; iz < nz+pmlout+marg; iz++) {
		vxn0[ix][iz] = vxn1[ix][iz] + dt/denx[ix][iz]*ldx(txxn0, ix, iz);
		vzn0[ix][iz] = vzn1[ix][iz] + dt/denz[ix][iz]*ldz(txxn0, ix, iz);
	    }
	}

	/*Velocity PML */
	pml_vxzb(vxn1, vzn1, vxn0, vzn0, txxn0, denx, denz, ldx, ldz, freesurface);

	/*n1 -> n0*/
	time_step_exch(txxn1, txxn0, it);
	time_step_exch(vxn1, vxn0, it);
	time_step_exch(vzn1, vzn0, it);
	pml_tstep_exchb(it);
	
	if ( wantwf && it%snpint == 0 ) {

	    for ( ix = 0; ix < nx; ix++) 
		sf_floatwrite(txxn0[ix+pmlout+marg]+pmlout+marg, nz, Ftmpbwf);
	}

	if (it%snpint == 0 ) {
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	    for (ix=0; ix<nx; ix++) {
		for (iz=0; iz<nz; iz++) {
		    ccr[ix][iz] += wavfld[wfit][ix][iz]*txxn0[ix+pmlout+marg][iz+pmlout+marg];
		}
	    }
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif
	    for (ix=0; ix<nx; ix++) {
		for (iz=0; iz<nz; iz++) {
		    sill[ix][iz] += wavfld[wfit][ix][iz]*wavfld[wfit][ix][iz];
		}
	    }
	    wfit--;
	}
    } /*Main loop*/
    if (verb) sf_warning(".");
    
#ifdef _OPENMP
#pragma omp parallel for private(ix, iz)
#endif    
    for (ix=0; ix<nx; ix++) {
	for (iz=0; iz<nz; iz++) {
	    img2[ix][iz] = ccr[ix][iz]/(sill[ix][iz]+SF_EPS);//
	}
    } 
    
    return 0;

}