Пример #1
0
int main(int argc, char* argv[])
{
    int nx, nf, i2, n2, lag, niter;
    bool single, verb;
    float eps;
    sf_complex *xx, *yy, *ff;
    sf_file in, out, filt;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");
    filt = sf_input("filt");

    if (SF_COMPLEX != sf_gettype(in) ||
	SF_COMPLEX != sf_gettype(filt)) sf_error("Need float input");
    if (!sf_histint(in,"n1",&nx)) sf_error("No n1= in input");
    n2 = sf_leftsize(in,1);

    if (!sf_histint(filt,"n1",&nf)) sf_error("No n1= in filtin");

    xx = sf_complexalloc(nx);
    ff = sf_complexalloc(nf);

    if (!sf_getbool("single",&single)) single=true;
    /* single channel or multichannel */

    if (!sf_getint("lag",&lag)) lag=1;
    /* lag for internal convolution */

    yy = sf_complexalloc(nx);

    if (!sf_getfloat("eps",&eps)) eps=1.0f;
    /* regularizion parameter */

    if (!sf_getint("niter",&niter)) niter=100;
    /* number of iterations */

    if (!sf_getbool("verb",&verb)) verb=false;
    /* verbosity flag */

    if (!single) sf_complexread (ff,nf,filt);

    for (i2=0; i2 < n2; i2++) {
        if (single) sf_complexread (ff,nf,filt);
        sf_complexread (xx,nx,in);

	cicai1_init(nf,ff,lag);

	sf_csolver_reg(sf_ccopy_lop,sf_ccgstep,cicai1_lop,nx,nx,nx,yy,xx,niter,eps,"verb",verb,"end");
	sf_ccgstep_close();
	
	sf_complexwrite (yy,nx,out);
    }
    
    exit(0);
}
Пример #2
0
int main(int argc, char* argv[])
{
    bool verb;
    int j, k, n, n2, i3, n3, iter, niter;
    sf_complex **a=NULL, *e=NULL;
    float s2;
    sf_file mat=NULL, val=NULL;

    sf_init(argc,argv);
    mat = sf_input("in");
    val = sf_output("out");

    if (SF_COMPLEX != sf_gettype(mat)) sf_error("Need complex input");
    if (!sf_histint(mat,"n1",&n)) sf_error("No n1= in input");
    if (!sf_histint(mat,"n2",&n2) || n2 != n) sf_error("Need n1=n2 in input");
    n3 = sf_leftsize(mat,2);

    sf_putint(val,"n2",1);

    if (!sf_getint("niter",&niter)) niter=10;
    if (!sf_getbool("verb",&verb)) verb=false;

    a = sf_complexalloc2(n,n);
    e = sf_complexalloc(n);
    jacobi2_init(n,verb);

    for (i3=0; i3 < n3; i3++) {
	sf_complexread(a[0],n*n,mat);
	
	for (iter=0; iter < niter; iter++) {
	    s2 = 0.;
	    for (j=0; j < n; j++) {
		for (k=0; k < n; k++) {
		    s2 += jacobi2(a,n,j,k);
		}
	    }
	    sf_warning("iter=%d s2=%g",iter+1,s2);
	}

	for (j=0; j < n; j++) {
	    e[j]=a[j][j];
	}
	
	sf_complexwrite(e,n, val);
    }

    exit(0);
}
Пример #3
0
int main(int argc, char* argv[])
{
    bool single;
    int n1, i2, n2, nf, nc;
    sf_complex *trace, *a;
    sf_file in, out;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");

    if (SF_COMPLEX != sf_gettype(in)) sf_error("Need complex input");
    if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input");

    if (!sf_getbool("single",&single)) single=true;
    /* single channel or multichannel */

    if (single) {
	nc = 1;
	n2 = sf_leftsize(in,1);
    } else {
	if (!sf_histint(in,"n2",&nc)) nc=1;
	n2 = sf_leftsize(in,2);
	sf_putint(out,"n2",1);
    }

    if (!sf_getint("nf",&nf)) sf_error("Need nf=");
    /* filter length */
    sf_putint(out,"n1",nf);

    cburg_init(n1,nc,nf);

    trace = sf_complexalloc(n1*nc);
    a = sf_complexalloc(nf);

    for (i2=0; i2 < n2; i2++) {
	sf_complexread(trace,n1*nc,in);

	cburg_apply(trace,a);

	sf_complexwrite(a,nf,out);
    }

    exit(0);
}
Пример #4
0
int main(int argc, char* argv[])
{
    bool impresp;
    int nt,nx,nz,nw,init,i,padfactor,nfilt,nkol,it,ix,iz,iw;
    float v,dx,dz,lambda,sixth,gamma,epsdamp,pi2,dw,dt, w,wov;
    sf_complex wov2, a, b, c, d, cshift;
    float ***ppp;
    sf_complex *pp, *qq;
    cfilter aa, fac1, fac2;
    sf_file out, imp=NULL;

    sf_init(argc,argv);
    out = sf_output("out");
    sf_setformat(out,"native_float");

    if (!sf_getint("nz",&nz)) nz=96;
    if (!sf_getint("nx",&nx)) nx=48;
    if (!sf_getint("nt",&nt)) nt=12;
    if (!sf_getint("nw",&nw)) nw=2;
    if (!sf_getint("init",&init)) init=1;

    if (!sf_getfloat("v",&v)) v=1.;
    if (!sf_getfloat("dz",&dz)) dz=1.;
    if (!sf_getfloat("dx",&dx)) dx=2.;
    if (!sf_getfloat("lambda",&lambda)) lambda=nz*dz/4.;

    sf_putint(out,"n1",nz);
    sf_putint(out,"n2",nx);
    sf_putint(out,"n3",nt);

    aa = allocatechelix(9);

    if (!sf_getfloat("sixth",&sixth)) sixth=0.0833;
    if (!sf_getfloat("gamma",&gamma)) gamma=0.667;
    if (!sf_getfloat("epsdamp",&epsdamp)) epsdamp=0.01;
    if (!sf_getint("padfactor",&padfactor)) padfactor=1024;
    if (!sf_getint("nfilt",&nfilt)) nfilt=nx+2;
    if (!sf_getbool("impresp",&impresp)) impresp=false;

    if (impresp) {
	imp = sf_output("imp");
	sf_setformat(imp,"native_complex");
	sf_putint(imp,"n1",2*nx);
	sf_putint(imp,"n2",2);
    }

    ppp = sf_floatalloc3(nz,nx,nt);
    pp = sf_complexalloc(nx*nz);
    qq = sf_complexalloc(nx*nz);

    pi2 = 2.*SF_PI;
    dw = v*pi2/lambda;
    dt =   pi2/(nt*dw);

    nkol=pad2(padfactor*nx);
    /* dkol=pi2/nkol; */

    for (it=0; it < nt; it++) {
	for (ix=0; ix < nx; ix++) {
	    for (iz=0; iz < nz; iz++) {
		ppp[it][ix][iz] = 0.;
	    }
	}
    }

    fac1 = allocatechelix(nfilt);
    fac2 = allocatechelix(nfilt);
    helimakelag(fac1,nx,nz);
    helimakelag(fac2,nx,nz);

    xkolmog_init(nkol);

    for (iw=0; iw < nw; iw++) { /* frequency loop */
	w = (iw+1)*dw;

	if (impresp) w=dw*nw/2;

	wov = w/v;
	wov2 = sf_cmplx(epsdamp,wov);
#ifdef SF_HAS_COMPLEX_H
	wov2 = -wov2*wov2;
#else
	wov2 = sf_cneg(sf_cmul(wov2,wov2));
#endif

	sf_warning("%g %g (%d of %d)",crealf(wov2),cimagf(wov2),iw,nw);

	init_wave(init,nx,dx,nz,dz,pp,wov,nw,iw);

	for (iz=0; iz < nx*nz; iz++) {
	    qq[iz]=sf_cmplx(0.,0.);
	}

	/* isotropic laplacian = 5-point laplacian */
	a= sf_cmplx(0.,0.);
#ifdef SF_HAS_COMPLEX_H
	b= gamma*(1+sixth*wov2)* (-1./(dz*dz));
	c= gamma*(1+sixth*wov2)* (-1./(dx*dx));
	d= gamma*(1+sixth*wov2)* (2/(dx*dx) + 2/(dz*dz))  -wov2;
#else
	b = sf_crmul(sf_cadd(sf_cmplx(1.,0.),sf_crmul(wov2,sixth)),
		     gamma*(-1./(dz*dz)));
	c = sf_crmul(sf_cadd(sf_cmplx(1.,0.),sf_crmul(wov2,sixth)),
		     gamma*(-1./(dx*dx)));
	d = sf_cadd(sf_crmul(sf_cadd(sf_cmplx(1.,0.),sf_crmul(wov2,sixth)),
			     gamma*(2/(dx*dx) + 2/(dz*dz))),sf_cneg(wov2));
#endif

	/* + rotated 5-point laplacian */
#ifdef SF_HAS_COMPLEX_H
	a += (1-gamma)*(1+sixth*wov2)* (-0.5/(dx*dz));
	b += (1-gamma)*(1+sixth*wov2)*0.;
	c += (1-gamma)*(1+sixth*wov2)*0.;
	d += (1-gamma)*(1+sixth*wov2)* 2.0/(dx*dz);
#else
	a = sf_cadd(a,sf_crmul(sf_cadd(sf_cmplx(1.0,0.0),
				       sf_crmul(wov2,sixth)),
			       (1-gamma)*(-0.5/(dx*dz))));
	d = sf_cadd(d,sf_crmul(sf_cadd(sf_cmplx(1.0,0.0),
				       sf_crmul(wov2,sixth)),
			       (1-gamma)*(2.0/(dx*dz))));
#endif

	aa->flt[0] = a; aa->lag[0] = -nx-1;
	aa->flt[1] = b; aa->lag[1] = -nx;
	aa->flt[2] = a; aa->lag[2] = -nx+1;

	aa->flt[3] = c; aa->lag[3] = -1;
	aa->flt[4] = d; aa->lag[4] = 0;
	aa->flt[5] = c; aa->lag[5] = 1;

	aa->flt[6] = a; aa->lag[6] = nx-1;
	aa->flt[7] = b; aa->lag[7] = nx;
	aa->flt[8] = a; aa->lag[8] = nx+1;

	xkolmog_helix(aa,fac1,fac2);

	for (i=0; i < nfilt; i++) {
#ifdef SF_HAS_COMPLEX_H
	    fac1->flt[i]=0.5*(fac2->flt[i]+conjf(fac1->flt[i]));
#else
	    fac1->flt[i]=sf_crmul(sf_cadd(fac2->flt[i],conjf(fac1->flt[i])),
				  0.5);
#endif
	}

	if (impresp) {
	    for (iz=0; iz < nx*nz; iz++) {
		pp[iz]=sf_cmplx(0.,0.);
	    }	    
	    pp[nx/2-1]=sf_cmplx(1.,0.);
	    sf_complexwrite(pp,2*nx,imp);
	}

	
	cpolydiv_init(nx*nz,fac2);
	cpolydiv_lop(false,false,nx*nz,nx*nz,pp,qq);

	if (impresp) {
	    sf_complexwrite(qq,2*nx,imp);
	    break;
	}

	/* back to time domain */
	for (it=0; it < nt; it++) {
	    cshift = cexpf(sf_cmplx( 0.,-w*it*dt));
	    for (ix=0; ix < nx; ix++) {
		for (iz=0; iz < nz; iz++) {
#ifdef SF_HAS_COMPLEX_H
		    ppp[it][ix][iz] += crealf(qq[ix+iz*nx]*cshift);
#else
		    ppp[it][ix][iz] += crealf(sf_cmul(qq[ix+iz*nx],cshift));
#endif
		}
	    }
	}

    } /* end frequency loop */

    sf_floatwrite(ppp[0][0],nt*nx*nz,out);

    exit(0);
}
Пример #5
0
void sf_add(sf_file out, int jobs)
/*< add outputs >*/
{
    int *ibuf=NULL, job, i;
    float *fbuf=NULL;
    char buffout[BUFSIZ];
    sf_complex *cbuf=NULL;
    sf_datatype type;
    size_t nbuf=BUFSIZ;
    off_t nsiz;
    char *oname;
    sf_file *ins;

    type = sf_gettype(out);

    switch(type) {
	case SF_FLOAT:
	    fbuf = (float*) buffout;
	    nbuf /= sizeof(float);
	    for (i=0; i < nbuf; i++) {
		fbuf[i] = 0.0f;
	    }
	    break;
	default:
	    sf_error("wrong type");
	    break;
    }

    ins = (sf_file*) sf_alloc(jobs,sizeof(sf_file));

    for (job=0; job < jobs; job++) {
	oname = onames[job];
	ins[job] = sf_input(oname);
    }

    for (nsiz = size2; nsiz > 0; nsiz -= nbuf) {
	if (nbuf > nsiz) nbuf=nsiz;

	for (job=0; job < jobs; job++) {
	    switch(type) {
		case SF_FLOAT:
		    sf_floatread((float*) buffer,nbuf,ins[job]);
		    for (i=0; i < nbuf; i++) {
			if (job) {
			    fbuf[i] += ((float*) buffer)[i];
			} else {
			    fbuf[i] = ((float*) buffer)[i];
			}
		    }
		    break;
		default:
		    sf_error("wrong type");
		    break;  
	    }
	}

	switch(type) {
	    case SF_FLOAT:
		sf_floatwrite(fbuf,nbuf,out);
		break;
	    case SF_COMPLEX:
		sf_complexwrite(cbuf,nbuf,out);
		break;
	    case SF_INT:
		sf_intwrite(ibuf,nbuf,out);
		break;
	    default:
		sf_error("wrong type");
		break;
	}
    }

    for (job=0; job < jobs; job++) {
	sf_fileclose(ins[job]);
	sf_rm(inames[job],true,false,false);
	sf_rm(onames[job],true,false,false);
	for (i=0; i < inpargc; i++) {
	    oname = inpnames[job][i];
	    sf_rm(oname,true,false,false);
	}
    }

    free(ins);
}
Пример #6
0
/* main function */
int main(int argc, char* argv[]) 
{
    /*geopar variables*/
    int nx, nz;
    int nxb, nzb;
    float dx, dz, ox, oz;
    int spz, gpz, gpl; /*source/geophone location*/
    int snpint;
    int top, bot, lft, rht; /*abc boundary*/
    int nt;
    float dt;
    float trunc; 
    bool verb; /* verbosity flag */
    bool illum; /* source illumination flag*/
    int m2, m2b, pad1;
    sf_complex **ltf, **rtf;
    sf_complex **ltb, **rtb;
    sf_complex *ww;
    float *rr;
    /*extras*/
    bool roll; /* survey strategy */
    int rectz,rectx,repeat; /*refl smoothing parameters*/
    int sht0,shtbgn,shtend,shtnum,shtnum0,shtint;
    /*mpi*/
    int cpuid, numprocs;

    /*misc*/
    int mode;
    int nzx, nx2, nz2, n2, nk;
    int ix, iz, it, is;
    int wfnt;
    float wfdt;
    int niter;

    /*Data/Image*/
    sf_complex ***record, **imginv;

    /*tmp*/
    int tmpint;

    /*I/O*/
    sf_file Fvel;
    sf_file left, right, leftb, rightb;
    sf_file Fsrc, Frcd/*source and record*/;
    sf_file Fimg;
    sf_file Fstart;

    /*axis*/
    sf_axis at, ax, az;

    MPI_Init(&argc, &argv);
    MPI_Comm_rank(MPI_COMM_WORLD, &cpuid);
    MPI_Comm_size(MPI_COMM_WORLD, &numprocs);

    sf_init(argc, argv);

    if(cpuid==0) sf_warning("numprocs=%d",numprocs);

    if (!sf_getbool("verb", &verb)) verb=false; /*verbosity*/
    if (!sf_getint("niter",&niter)) niter=1;
    if (!sf_getint("mode", &mode)) mode = 0;
    if (!sf_getbool("illum", &illum)) illum=false; /*if n, no source illumination applied */
    if (!sf_getbool("roll", &roll)) roll=false; /*if n, receiver is independent of source location and gpl=nx*/
    /* source/receiver info */
    if (!sf_getint("shtbgn", &shtbgn)) sf_error("Need shot starting location on grid!");
    if (!sf_getint("sht0", &sht0)) sht0=shtbgn; /*actual shot origin on grid*/
    if (!sf_getint("shtend", &shtend)) sf_error("Need shot ending location on grid!");
    if (!sf_getint("shtint", &shtint)) sf_error("Need shot interval on grid!");
    shtnum = (int)((shtend-shtbgn)/shtint) + 1;
    shtnum0 = shtnum;
    if (shtnum%numprocs!=0) {
        shtnum += numprocs-shtnum%numprocs;
        if (verb) sf_warning("Total shot number is not divisible by total number of nodes! shunum padded from %d to %d.",shtnum0,shtnum); }
    if (!sf_getint("spz", &spz)) sf_error("Need source depth!");
    if (!sf_getint("gpz", &gpz)) sf_error("Need receiver depth!");
    if (roll) if (!sf_getint("gpl", &gpl)) sf_error("Need receiver length");
    if (!sf_getint("snapinter", &snpint)) snpint=1;     /* snap interval */
    /*--- parameters of source ---*/
    if (!sf_getfloat("srctrunc", &trunc)) trunc=0.4;
    if (!sf_getint("rectz", &rectz)) rectz=1;
    if (!sf_getint("rectx", &rectx)) rectx=1;
    if (!sf_getint("repeat", &repeat)) repeat=0;
    /* abc parameters */
    if (!sf_getint("top", &top)) top=40;
    if (!sf_getint("bot", &bot)) bot=40;
    if (!sf_getint("lft", &lft)) lft=40;
    if (!sf_getint("rht", &rht)) rht=40;

    /*Set I/O file*/
    Frcd = sf_input("--input"); /*record from elsewhere*/
    Fsrc  = sf_input("src");   /*source wavelet*/      
    Fimg  = sf_output("--output");
    left  = sf_input("left");
    right = sf_input("right");
    leftb  = sf_input("leftb");
    rightb = sf_input("rightb");
    Fvel  = sf_input("vel");  /*velocity - just for model dimension*/

    /*--- Axes parameters ---*/
    at = sf_iaxa(Fsrc, 1); nt = sf_n(at);  dt = sf_d(at);
    az = sf_iaxa(Fvel, 1); nzb = sf_n(az); dz = sf_d(az); oz = sf_o(az);
    ax = sf_iaxa(Fvel, 2); nxb = sf_n(ax); dx = sf_d(ax); ox = sf_o(ax);
    nzx = nzb*nxb;
    nz = nzb - top - bot;
    nx = nxb - lft - rht;
    if (!roll) gpl = nx; /* global survey setting */
    /* wavefield axis */
    wfnt = (int)(nt-1)/snpint+1;
    wfdt = dt*snpint;

    /* propagator matrices */
    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */
    nz2 = kiss_fft_next_fast_size(nzb*pad1);
    nx2 = kiss_fft_next_fast_size(nxb);
    nk = nz2*nx2; /*wavenumber*/
    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);

    if (!sf_histint(leftb,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(leftb,"n2",&m2b))  sf_error("Need n2= in left");
    if (!sf_histint(rightb,"n1",&n2) || n2 != m2b) sf_error("Need n1=%d in right",m2b);
    if (!sf_histint(rightb,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);

    /*check record data*/
    sf_histint(Frcd,"n1", &tmpint);
    if (tmpint != nt ) sf_error("Error parameter n1 in record!");
    sf_histint(Frcd,"n2", &tmpint);
    if (tmpint != gpl ) sf_error("Error parameter n2 in record!");
    sf_histint(Frcd,"n3", &tmpint);
    if (tmpint != shtnum0 ) sf_error("Error parameter n3 in record!");

    /*check starting model for cg*/
    if (NULL!=sf_getstring("start"))
        Fstart = sf_input("start");
    else
        Fstart = NULL;

    /*allocate memory*/
    ww=sf_complexalloc(nt);
    rr=sf_floatalloc(nzx);
    ltf = sf_complexalloc2(nzx,m2);
    rtf = sf_complexalloc2(m2,nk);
    ltb = sf_complexalloc2(nzx,m2b);
    rtb = sf_complexalloc2(m2b,nk);
    geop = (geopar) sf_alloc(1, sizeof(*geop));
    record = sf_complexalloc3(nt, gpl, shtnum);
    imginv = sf_complexalloc2(nz,nx);

    /*read from files*/
    sf_complexread(ww,nt,Fsrc);
    sf_complexread(ltf[0],nzx*m2,left);
    sf_complexread(rtf[0],m2*nk,right);
    sf_complexread(ltb[0],nzx*m2b,leftb);
    sf_complexread(rtb[0],m2b*nk,rightb);
    /*read data*/
    sf_complexread(record[0][0], shtnum0*gpl*nt, Frcd);
    if (shtnum0%numprocs!=0) {
#ifdef _OPENMP
#pragma omp parallel for private(is,ix,it)
#endif
        for (is=shtnum0; is<shtnum; is++)
            for (ix=0; ix<gpl; ix++)
                for (it=0; it<nt; it++)
                    record[is][ix][it] = sf_cmplx(0.,0.);
    }
    /*read starting model*/
    if (NULL != Fstart) {
        sf_complexread(imginv[0],nx*nz,Fstart);
    } else {
        /*transform the dimension to 1d*/
#ifdef _OPENMP
#pragma omp parallel for private(iz)
#endif
        for (iz=0; iz<nz; iz++) {
            for (ix=0; ix<nx; ix++) {
                imginv[ix][iz] = sf_cmplx(0.,0.);
            }
        }
    }

    /* output RSF files */
    if (cpuid==0) {
        sf_setn(az, nz);
        sf_setn(ax, nx);
        sf_oaxa(Fimg, az, 1);
        sf_oaxa(Fimg, ax, 2);
        sf_settype(Fimg,SF_COMPLEX);
    }

    /*close RSF files*/
    sf_fileclose(Fvel);
    sf_fileclose(Fsrc);
    sf_fileclose(left);
    sf_fileclose(right);
    sf_fileclose(leftb);
    sf_fileclose(rightb);

    /*load geopar elements*/
    geop->nx  = nx;
    geop->nz  = nz;
    geop->nxb = nxb;
    geop->nzb = nzb;
    geop->dx  = dx;
    geop->dz  = dz;
    geop->ox  = ox;
    geop->oz  = oz;
    geop->snpint = snpint;
    geop->spz = spz;
    geop->gpz = gpz;
    geop->gpl = gpl;
    geop->top = top;
    geop->bot = bot;
    geop->lft = lft;
    geop->rht = rht;
    geop->nt = nt;
    geop->dt = dt;
    geop->trunc = trunc;
    /*geop->adj   = adj; */
    geop->verb  = verb;
    geop->illum = illum;
    geop->m2 = m2;
    geop->m2b = m2b;
    geop->pad1 = pad1;
    /*pointers*/
    geop->ltf = ltf;
    geop->rtf = rtf;
    geop->ltb = ltb;
    geop->rtb = rtb;
    geop->ww  = ww;
    geop->rr  = rr;
    /*extra*/
    geop->roll = roll;
    geop->rectz=rectz;
    geop->rectx=rectx;
    geop->repeat=repeat;
    geop->sht0=sht0;
    geop->shtbgn=shtbgn;
    geop->shtend=shtend;
    geop->shtnum=shtnum;
    geop->shtnum0=shtnum0;
    geop->shtint=shtint;
    geop->cpuid=cpuid;
    geop->numprocs=numprocs;
    /*switch*/
    geop->mode=mode;

    sf_csolver(psrtm_lop,sf_ccgstep,nz*nx,nt*gpl*shtnum,imginv[0],record[0][0],niter,"verb",true,"end");
    //psrtm_lop(true,false,nz*nx,nt*gpl*shtnum,imginv[0],record[0][0]);

    if (cpuid==0) sf_complexwrite(imginv[0], nz*nx, Fimg);

    /*free memory*/
    free(geop);
    free(ww); free(rr);
    free(*ltf); free(ltf);
    free(*rtf); free(rtf);
    free(*ltb); free(ltb);
    free(*rtb); free(rtb);
    free(*imginv); free(imginv);
    free(**record); free(*record); free(record);

    MPI_Finalize();
    exit(0);
}
Пример #7
0
int main(int argc, char* argv[])
{
    int i, n, n1;
    float *dat=NULL, *adat=NULL, t, pclip, d;
    sf_complex *cdat=NULL;
    sf_file in=NULL, out=NULL;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");

    n = sf_filesize(in);
    adat = sf_floatalloc(n);

    if (!sf_getfloat("pclip",&pclip)) sf_error("Need pclip=");
    /* percentage to clip */
    n1 = 0.5+n*(1.-0.01*pclip);
    if (n1 < 0) n1=0;
    if (n1 >= n) n1=n-1;

    if (SF_FLOAT == sf_gettype(in)) {
	dat = sf_floatalloc(n);
	sf_floatread(dat,n,in);
	for (i=0; i < n; i++) {
	    adat[i] = fabsf(dat[i]);
	}
    } else if (SF_COMPLEX == sf_gettype(in)) {
	cdat = sf_complexalloc(n);
	sf_complexread(cdat,n,in);
	for (i=0; i < n; i++) {
	    adat[i] = cabsf(cdat[i]);
	}
    } else {
	sf_error("Need float or complex input");
    }

    t = sf_quantile(n1,n,adat);

    if (NULL != dat) {
	for (i=0; i < n; i++) {
	    d = dat[i];
	    if (d < -t) {
		dat[i] = d+t;
	    } else if (d > t) {
		dat[i] = d-t;
	    } else {
		dat[i] = 0.;
	    }
	}
	sf_floatwrite(dat,n,out);
    } else {
	for (i=0; i < n; i++) {
	    d = cabsf(cdat[i]);
	    if (d < -t) {
#ifdef SF_HAS_COMPLEX_H
		cdat[i] *= (d+t)/d;
#else
		cdat[i] = sf_crmul(cdat[i],(d+t)/d);
#endif
	    } else if (d > t) {		
#ifdef SF_HAS_COMPLEX_H
		cdat[i] *= (d-t)/d;
#else
		cdat[i] = sf_crmul(cdat[i],(d-t)/d);
#endif
	    } else {
		cdat[i] = sf_cmplx(0.,0.);
	    }
	}
	sf_complexwrite(cdat,n,out);
    }

    exit(0);
}
Пример #8
0
int main(int argc, char* argv[])
{
    bool adj,timer,verb,gmres;
    int nt, nx, nz, nx2, nz2, nzx, nzx2, ntx, pad1, snap, gpz, wfnt, i;
    int m2, n2, nk, nth=1;
    int niter, mem;
    float dt, dx, dz, ox;
    sf_complex *img, *imgout, *dat, **lt1, **rt1, **lt2, **rt2, ***wvfld;
    sf_file data, image, leftf, rightf, leftb, rightb, snaps;
    double time=0.,t0=0.,t1=0.;
    geopar geop;

    sf_init(argc,argv);

    /* essentially doing imaging */
    adj = true;

    if (!sf_getbool("gmres",&gmres)) gmres=false;
    if (gmres) {
      if (!sf_getint("niter",&niter)) niter=10;
      if (!sf_getint("mem",&mem)) mem=20;
    }

    if(! sf_getbool("timer",&timer)) timer=false;
    if (!sf_getbool("verb",&verb)) verb=false;
    if (!sf_getint("snap",&snap)) snap=0;
    /* interval for snapshots */
    if (!sf_getint("pad1",&pad1)) pad1=1;
    /* padding factor on the first axis */
    if(!sf_getint("gpz",&gpz)) gpz=0;
    /* geophone surface */

    /* adj */
    if (!sf_getint("nz",&nz)) sf_error("Need nz=");
    /* depth samples */
    if (!sf_getfloat("dz",&dz)) sf_error("Need dz=");
    /* depth sampling */

    /* for */
    if (!sf_getint("nt",&nt)) sf_error("Need nt=");
    /* time samples */
    if (!sf_getfloat("dt",&dt)) sf_error("Need dt=");
    /* time sampling */

    if (adj) { /* migration */
	data = sf_input("in");
	image = sf_output("out");
	sf_settype(image,SF_COMPLEX);

	if (!sf_histint(data,"n1",&nt)) sf_error("No n1= in input");
	if (!sf_histfloat(data,"d1",&dt)) sf_error("No d1= in input");

	if (!sf_histint(data,"n2",&nx)) sf_error("No n2= in input");
	if (!sf_histfloat(data,"d2",&dx)) sf_error("No d2= in input");
	if (!sf_histfloat(data,"o2",&ox)) ox=0.; 

	sf_putint(image,"n1",nz);
	sf_putfloat(image,"d1",dz);
	sf_putfloat(image,"o1",0.);
	sf_putstring(image,"label1","Depth");

	sf_putint(image,"n2",nx);
	sf_putfloat(image,"d2",dx);
	sf_putfloat(image,"o2",ox);
	sf_putstring(image,"label2","Distance");
    } else { /* modeling */
	image = sf_input("in");
	data = sf_output("out");
	sf_settype(data,SF_COMPLEX);

	if (!sf_histint(image,"n1",&nz)) sf_error("No n1= in input");
	if (!sf_histfloat(image,"d1",&dz)) sf_error("No d1= in input");

	if (!sf_histint(image,"n2",&nx))  sf_error("No n2= in input");
	if (!sf_histfloat(image,"d2",&dx)) sf_error("No d2= in input");
	if (!sf_histfloat(image,"o2",&ox)) ox=0.; 	

	if (!sf_getint("nt",&nt)) sf_error("Need nt=");
	/* time samples */
	if (!sf_getfloat("dt",&dt)) sf_error("Need dt=");
	/* time sampling */

	sf_putint(data,"n1",nt);
	sf_putfloat(data,"d1",dt);
	sf_putfloat(data,"o1",0.);
	sf_putstring(data,"label1","Time");
	sf_putstring(data,"unit1","s");

	sf_putint(data,"n2",nx);
	sf_putfloat(data,"d2",dx);
	sf_putfloat(data,"o2",ox);
	sf_putstring(data,"label2","Distance");
    }

    nz2 = kiss_fft_next_fast_size(nz*pad1);
    nx2 = kiss_fft_next_fast_size(nx);
    nk = nz2*nx2; /*wavenumber*/

    nzx = nz*nx;
    nzx2 = nz2*nx2;
    ntx = nt*nx;

    if (snap > 0) {
        wfnt = (int)(nt-1)/snap+1;
	snaps = sf_output("snaps");
	/* (optional) snapshot file */
	sf_settype(snaps,SF_COMPLEX);
	sf_putint(snaps,"n1",nz);
	sf_putfloat(snaps,"d1",dz);
	sf_putfloat(snaps,"o1",0.);
	sf_putstring(snaps,"label1","Depth");
	sf_putint(snaps,"n2",nx);
	sf_putfloat(snaps,"d2",dx);
	sf_putfloat(snaps,"o2",ox);
	sf_putstring(snaps,"label2","Distance");
	sf_putint(snaps,"n3",wfnt);
	sf_putfloat(snaps,"d3",dt*snap);
	sf_putfloat(snaps,"o3",0.);
	sf_putstring(snaps,"label3","Time");
    } else {
        wfnt = 0;
	snaps = NULL;
    }

    /* propagator matrices */
    leftf = sf_input("leftf");
    rightf = sf_input("rightf");
    
    if (!sf_histint(leftf,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in leftf",nzx);
    if (!sf_histint(leftf,"n2",&m2))  sf_error("No n2= in leftf");
    if (!sf_histint(rightf,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in rightf",m2);
    if (!sf_histint(rightf,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in rightf",nk);

    leftb = sf_input("leftb");
    rightb = sf_input("rightb");
    
    if (!sf_histint(leftb,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in leftb",nzx);
    if (!sf_histint(leftb,"n2",&m2))  sf_error("No n2= in leftb");
    if (!sf_histint(rightb,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in rightb",m2);
    if (!sf_histint(rightb,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in rightb",nk);
    
    lt1 = sf_complexalloc2(nzx,m2); /* propagator for forward modeling */
    rt1 = sf_complexalloc2(m2,nk);
    lt2 = sf_complexalloc2(nzx,m2); /* propagator for backward imaging */
    rt2 = sf_complexalloc2(m2,nk);
    img = sf_complexalloc(nz*nx);
    dat = sf_complexalloc(nt*nx);
    imgout = sf_complexalloc(nz*nx);
    if (snap > 0) wvfld = sf_complexalloc3(nz,nx,wfnt);
    else wvfld = NULL;
    geop = (geopar) sf_alloc(1, sizeof(*geop));

    sf_complexread(lt1[0],nzx*m2,leftf);
    sf_complexread(rt1[0],m2*nk,rightf);
    sf_complexread(lt2[0],nzx*m2,leftb);
    sf_complexread(rt2[0],m2*nk,rightb);
    if (adj) sf_complexread(dat,ntx,data);
    else sf_complexread(img,nzx,image);

    /*close RSF files*/
    sf_fileclose(leftf);
    sf_fileclose(rightf);
    sf_fileclose(leftb);
    sf_fileclose(rightb);

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

    if (timer) t0 = gtod_timer();

    /*load constant geopar elements*/
    geop->nx  = nx;
    geop->nz  = nz;
    geop->dx  = dx;
    geop->dz  = dz;
    geop->ox  = ox;
    geop->gpz = gpz;
    geop->nt  = nt;
    geop->dt  = dt;
    geop->snap= snap;
    geop->nzx2= nzx2;
    geop->nk  = nk;
    geop->m2  = m2;
    geop->wfnt= wfnt;
    geop->pad1= pad1;
    geop->verb= verb;

    /* first get the Q-compensated image: B[d] */
    lrexp(img, dat, adj, lt2, rt2, geop, wvfld);

    /* performing the least-squares optimization: ||{BF}[m] - B[d]|| */
    if (gmres) {
      /* disabling snapshots */
      geop->snap= 0;
      lrexp_init(lt1,rt1,lt2,rt2);

      sf_warning(">>>>>> Using GMRES(m) <<<<<<");
      cgmres_init(nzx,mem);
      cgmres( img, imgout, lrexp_op, geop, niter, 0.01*SF_EPS, true);
      /*lrexp_op(nzx, img, imgout, geop);*/
      lrexp_close();
    } else {
      for (i=0; i<nzx; i++)
	imgout[i] = img[i];
    }

    if (timer)
      {
        t1 = gtod_timer();
        time = t1-t0;
        sf_warning("Time = %lf\n",time);
      }

    if (adj) {
	sf_complexwrite(imgout,nzx,image);
    } else {
	sf_complexwrite(dat,ntx,data);
    }
    
    if (snap > 0 && NULL != snaps) {
	sf_complexwrite(wvfld[0][0],wfnt*nx*nz,snaps);
    }

    exit(0);
}
Пример #9
0
int main(int argc, char* argv[])
{
    int nw, nx, ny, iw, ix, iy;
    sf_complex *oper=NULL;
    float dw,dx,dy, ow,ox,oy, w,x,y, x1,x2, h1,h2,f1,f2, maxe;
    float eps1,eps2,amp1,amp2,phase1,phase2,amp;
    sf_file in=NULL, out=NULL;

    sf_init (argc,argv);
    in = sf_input("in");
    out = sf_output("out");

    if (SF_COMPLEX != sf_gettype(in)) sf_error("Need complex input");
    if (!sf_histint(in,"n1",&nw)) sf_error("No n1= in input");
    if (!sf_histint(in,"n2",&nx)) sf_error("No n2= in input");
    if (!sf_histint(in,"n3",&ny)) sf_error("No n3= in input");

    if (!sf_histfloat (in,"o1",&ow)) sf_error("No o1= in input");
    if (!sf_histfloat (in,"d1",&dw)) sf_error("No d1= in input");
    if (!sf_histfloat (in,"o2",&ox)) sf_error("No o2= in input");
    if (!sf_histfloat (in,"d2",&dx)) sf_error("No d2= in input");
    if (!sf_histfloat (in,"o3",&oy)) sf_error("No o3= in input");
    if (!sf_histfloat (in,"d3",&dy)) sf_error("No d3= in input");

    if (!sf_getfloat("h1",&h1)) sf_error("Need h1=");
    /* input offset */
    if (!sf_getfloat("h2",&h2)) sf_error("Need h2=");
    /* output offset */
    if (!sf_getfloat("f1",&f1)) sf_error("Need f1=");
    /* input azimuth in degrees */
    if (!sf_getfloat("f2",&f2)) sf_error("Need f2=");
    /* output azimuth in degrees */

    if (!sf_getfloat("maxe",&maxe)) maxe=10.;
    /* stability constraint */

    f1 *= SF_PI/180.;
    f2 *= SF_PI/180.;

    oper = sf_complexalloc (nw);

    for (iy=0; iy < ny; iy++) {
	y = oy + iy*dy;
	for (ix=0; ix < nx; ix++) {
	    x = ox + ix*dx;
	    x1 = x*cosf(f1) + y*sinf(f1);
	    x2 = x*cosf(f2) + y*sinf(f2);
	    for (iw=0; iw < nw; iw++) {
		w = ow + iw*dw;
		if (fabsf (w) > FLT_EPSILON) {
		    eps1 = 2.*fabsf(x1*h1/w);
		    eps2 = 2.*fabsf(x2*h2/w);
		    if (eps1 <= maxe && eps2 <= maxe) {
			eps1 = hypotf (1.,eps1);
			eps2 = hypotf (1.,eps2);

			amp1 = 1./eps1+eps1;
			amp2 = 1./eps2+eps2;
			phase1 = 1-eps1+logf(0.5*(1.+eps1));
			phase2 = 1-eps2+logf(0.5*(1.+eps2));

			amp = expf(0.5*(eps1-logf(amp1)+logf(amp2)-eps2));

			phase1 = SF_PI*(phase2-phase1)*w;
			oper[iw] = sf_cmplx(amp*cosf(phase1),amp*sinf(phase1));
		    } else {
			oper[iw] = sf_cmplx(0.,0.);
		    }
		} else {
		    oper[iw] = sf_cmplx(0.,0.);
		}
	    }
	    sf_complexwrite (oper,nw,out);
	}
    }

    exit (0);
}
Пример #10
0
int main(int argc, char* argv[])
{
    bool adj,timer,verb;
    int nt, nx, nz, nx2, nz2, nzx, nzx2, ntx, pad1, snap, wfnt;
    int m2, n2, nk, nth=1;
    float dt, dx, dz, ox;
    sf_complex **img, **dat, **lt, **rt, ***wvfld, *ww;
    sf_file data, image, left, right, snaps, src;
    double time=0.,t0=0.,t1=0.;
    geopar geop;

    sf_init(argc,argv);

    if (!sf_getbool("adj",&adj)) adj=false;
    /* if n, modeling; if y, migration */
    if(! sf_getbool("timer",&timer)) timer=false;
    if (!sf_getbool("verb",&verb)) verb=false;
    if (!sf_getint("snap",&snap)) snap=0;
    /* interval for snapshots */
    if (!sf_getint("pad1",&pad1)) pad1=1;
    /* padding factor on the first axis */

    if (adj) { /* migration */
	data = sf_input("in"); // data here is just a refl file
	image = sf_output("out");
	sf_settype(image,SF_COMPLEX);

	if (!sf_histint(data,"n1",&nz)) sf_error("No n1= in input");
	if (!sf_histfloat(data,"d1",&dz)) sf_error("No d1= in input");
	if (!sf_histint(data,"n2",&nx)) sf_error("No n2= in input");
	if (!sf_histfloat(data,"d2",&dx)) sf_error("No d2= in input");
	if (!sf_histfloat(data,"o2",&ox)) ox=0.; 

	if (!sf_getint("nt",&nt)) sf_error("Need nt=");
	/* time samples */
	if (!sf_getfloat("dt",&dt)) sf_error("Need dt=");
	/* time sampling */

	sf_putint(image,"n1",nz);
	sf_putfloat(image,"d1",dz);
	sf_putfloat(image,"o1",0.);
	sf_putstring(image,"label1","Depth");
	sf_putint(image,"n2",nx);
	sf_putfloat(image,"d2",dx);
	sf_putfloat(image,"o2",ox);
	sf_putstring(image,"label2","Distance");
    } else { /* modeling */
	image = sf_input("in");
	data = sf_output("out");
	src = sf_input("src");
	sf_settype(data,SF_COMPLEX);

	if (!sf_histint(image,"n1",&nz)) sf_error("No n1= in input");
	if (!sf_histfloat(image,"d1",&dz)) sf_error("No d1= in input");
	if (!sf_histint(image,"n2",&nx))  sf_error("No n2= in input");
	if (!sf_histfloat(image,"d2",&dx)) sf_error("No d2= in input");
	if (!sf_histfloat(image,"o2",&ox)) ox=0.; 	

	if (!sf_getint("nt",&nt)) sf_error("Need nt=");
	/* time samples */
	if (!sf_getfloat("dt",&dt)) sf_error("Need dt=");
	/* time sampling */
	if (!sf_histint(src,"n1",&n2) || n2 != nt) sf_error("nt doesn't match!");

	sf_putint(data,"n1",nz);
	sf_putfloat(data,"d1",dz);
	sf_putfloat(data,"o1",0.);
	sf_putstring(data,"label1","Depth");
	sf_putint(data,"n2",nx);
	sf_putfloat(data,"d2",dx);
	sf_putfloat(data,"o2",ox);
	sf_putstring(data,"label2","Distance");
    }

    nz2 = kiss_fft_next_fast_size(nz*pad1);
    nx2 = kiss_fft_next_fast_size(nx);
    nk = nz2*nx2; /*wavenumber*/

    nzx = nz*nx;
    nzx2 = nz2*nx2;
    ntx = nt*nx;
    wfnt = (int)(nt-1)/snap+1;

    if (snap > 0) {
	snaps = sf_output("snaps");
	/* (optional) snapshot file */
	sf_settype(snaps,SF_COMPLEX);
	sf_putint(snaps,"n1",nz);
	sf_putfloat(snaps,"d1",dz);
	sf_putfloat(snaps,"o1",0.);
	sf_putstring(snaps,"label1","Depth");
	sf_putint(snaps,"n2",nx);
	sf_putfloat(snaps,"d2",dx);
	sf_putfloat(snaps,"o2",ox);
	sf_putstring(snaps,"label2","Distance");
	sf_putint(snaps,"n3",wfnt);
	sf_putfloat(snaps,"d3",dt*snap);
	sf_putfloat(snaps,"o3",0.);
	sf_putstring(snaps,"label3","Time");
    } else {
	snaps = NULL;
    }

    /* propagator matrices */
    left = sf_input("left");
    right = sf_input("right");
    
    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("No n2= in left");
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);
    
    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);
    img = sf_complexalloc2(nz,nx);
    dat = sf_complexalloc2(nz,nx);
    if (snap > 0) wvfld = sf_complexalloc3(nz,nx,wfnt);
    else wvfld = NULL;
    geop = (geopar) sf_alloc(1, sizeof(*geop));
    if (!adj) {
	ww=sf_complexalloc(nt);
	sf_complexread(ww,nt,src);
    } else ww=NULL;
    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);
    if (adj) sf_complexread(dat[0],nzx,data);
    else sf_complexread(img[0],nzx,image);

    /*close RSF files*/
    sf_fileclose(left);
    sf_fileclose(right);

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

    if (timer) t0 = gtod_timer();

    /*load constant geopar elements*/
    geop->nx  = nx;
    geop->nz  = nz;
    geop->dx  = dx;
    geop->dz  = dz;
    geop->ox  = ox;
    geop->nt  = nt;
    geop->dt  = dt;
    geop->snap= snap;
    geop->nzx2= nzx2;
    geop->nk  = nk;
    geop->m2  = m2;
    geop->wfnt= wfnt;

    lrexp(img, dat, adj, lt, rt, ww, geop, pad1, verb, snap, wvfld);

    if (timer)
      {
        t1 = gtod_timer();
        time = t1-t0;
        sf_warning("Time = %lf\n",time);
      }

    if (adj) {
	sf_complexwrite(img[0],nzx,image);
    } else {
	sf_complexwrite(dat[0],ntx,data);
    }
    
    if (snap > 0 && NULL != snaps) {
	sf_complexwrite(wvfld[0][0],wfnt*nx*nz,snaps);
    }

    exit(0);
}
Пример #11
0
int main(int argc, char* argv[])
{
    /*------------------------------------------------------------*/
    /* Execution control, I/O files and geometry                  */
    /*------------------------------------------------------------*/
    bool verb,fsrf,snap,back,esou; /* execution flags */
    int  jsnap,ntsnap,jdata; /* jump along axes */
    int  shft; /* time shift for wavefield matching in RTM */

    /* I/O files */
    sf_file Fwav=NULL; /* wavelet   */
    sf_file Fdat=NULL; /* data      */
    sf_file Fsou=NULL; /* sources   */
    sf_file Frec=NULL; /* receivers */
    sf_file Fccc=NULL; /* velocity  */
    sf_file Frkp=NULL; /* app. rank */
    sf_file Fltp=NULL; /* left mat  */
    sf_file Frtp=NULL; /* right mat */
    sf_file Fwfp=NULL; /* wavefield */
    sf_file Frks=NULL; /* app. rank */
    sf_file Flts=NULL; /* left mat  */
    sf_file Frts=NULL; /* right mat */
    sf_file Fwfs=NULL; /* wavefield */

    /* cube axes */
    sf_axis at,ax,ay,az; /* time, x, y, z */ 
    sf_axis asx,asy,arx,ary,ac;    /* sou, rec-x, rec-y, component */ 

    /* dimension, index and interval */
    int     nt,nz,nx,ny,ns,nr,nc,nb;
    int     it,iz,ix,iy;
    float   dt,dz,dx,dy;
    int     nxyz, nk;

    /* FDM and KSP structure */ //!!!JS
    fdm3d    fdm=NULL;
    dft3d    dft=NULL;
    clr3d    clr_p=NULL, clr_s=NULL;

    /* I/O arrays for sou & rec */
    sf_complex***ww=NULL;    /* wavelet   */
    pt3d        *ss=NULL;    /* sources   */
    pt3d        *rr=NULL;    /* receivers */
    sf_complex **dd=NULL;    /* data      */

    /*------------------------------------------------------------*/
    /* displacement: uo = U @ t; up = U @ t+1                     */
    /*------------------------------------------------------------*/
    sf_complex ***uox, ***uoy, ***uoz, **uo;
    sf_complex ***uox_p, ***uoy_p, ***uoz_p, **uo_p;
    sf_complex ***uox_s, ***uoy_s, ***uoz_s, **uo_s;
    /*sf_complex ***upx, ***upy, ***upz, **up;*/

    /*------------------------------------------------------------*/
    /* lowrank decomposition arrays                               */
    /*------------------------------------------------------------*/
    int ntmp, *n2s_p, *n2s_s;
    sf_complex **lt_p, **rt_p, **lt_s, **rt_s;

    /*------------------------------------------------------------*/
    /* linear interpolation weights/indices                       */
    /*------------------------------------------------------------*/
    lint3d cs,cr; /* for injecting source and extracting data */

    /* Gaussian bell */
    int nbell;
    
    /*------------------------------------------------------------*/
    /* wavefield cut params                                       */
    /*------------------------------------------------------------*/
    sf_axis   acz=NULL,acx=NULL,acy=NULL;
    int       nqz,nqx,nqy;
    float     oqz,oqx,oqy;
    float     dqz,dqx,dqy;
    sf_complex***uc=NULL; /* tmp array for output wavefield snaps */

    /*------------------------------------------------------------*/
    /* init RSF                                                   */
    /*------------------------------------------------------------*/
    sf_init(argc,argv);

    /*------------------------------------------------------------*/
    /* OMP parameters                                             */
    /*------------------------------------------------------------*/
#ifdef _OPENMP
    omp_init();
#endif

    /*------------------------------------------------------------*/
    /* read execution flags                                       */
    /*------------------------------------------------------------*/
    if(! sf_getbool("verb",&verb)) verb=false; /* verbosity flag */
    if(! sf_getbool("snap",&snap)) snap=false; /* wavefield snapshots flag */
    if(! sf_getbool("free",&fsrf)) fsrf=false; /* free surface flag */
    if(! sf_getbool("back",&back)) back=false; /* backward extrapolation flag (for rtm) */
    if(! sf_getbool("esou",&esou)) esou=false; /* explosive force source */

    /*------------------------------------------------------------*/
    /* I/O files                                                  */
    /*------------------------------------------------------------*/
    Fwav = sf_input ("in" ); /* wavelet   */
    Fdat = sf_output("out"); /* data      */
    Fsou = sf_input ("sou"); /* sources   */
    Frec = sf_input ("rec"); /* receivers */
    Fccc = sf_input ("ccc"); /* stiffness */
    Frkp = sf_input ("rkp"); /* app. rank */
    Fltp = sf_input ("ltp"); /* left mat  */
    Frtp = sf_input ("rtp"); /* right mat */
    Fwfp = sf_output("wfp"); /* wavefield */
    Frks = sf_input ("rks"); /* app. rank */
    Flts = sf_input ("lts"); /* left mat  */
    Frts = sf_input ("rts"); /* right mat */
    Fwfs = sf_output("wfs"); /* wavefield */

    /*------------------------------------------------------------*/
    /* axes                                                       */
    /*------------------------------------------------------------*/
    at = sf_iaxa(Fwav,4); sf_setlabel(at,"t"); if(verb) sf_raxa(at); /* time */
    az = sf_iaxa(Fccc,1); sf_setlabel(az,"z"); if(verb) sf_raxa(az); /* depth */
    ax = sf_iaxa(Fccc,2); sf_setlabel(ax,"x"); if(verb) sf_raxa(ax); /* space x */
    ay = sf_iaxa(Fccc,3); sf_setlabel(ay,"y"); if(verb) sf_raxa(ay); /* space y */

    asx = sf_iaxa(Fsou,2); sf_setlabel(asx,"sx"); if(verb) sf_raxa(asx); /* sources x */
    asy = sf_iaxa(Fsou,3); sf_setlabel(asy,"sy"); if(verb) sf_raxa(asy); /* sources y */
    arx = sf_iaxa(Frec,2); sf_setlabel(arx,"rx"); if(verb) sf_raxa(arx); /* receivers x */
    ary = sf_iaxa(Frec,3); sf_setlabel(ary,"ry"); if(verb) sf_raxa(ary); /* receivers y */

    nt = sf_n(at); dt = sf_d(at);
    nz = sf_n(az); dz = sf_d(az);
    nx = sf_n(ax); dx = sf_d(ax);
    ny = sf_n(ay); dy = sf_d(ay);

    ns = sf_n(asx)*sf_n(asy);
    nr = sf_n(arx)*sf_n(ary);

    /*------------------------------------------------------------*/
    /* other execution parameters                                 */
    /*------------------------------------------------------------*/
    if(! sf_getint("nbell",&nbell)) nbell=NOP;  /* bell size */
    if(verb) sf_warning("nbell=%d",nbell);
    if(! sf_getint("jdata",&jdata)) jdata=1;
    if(snap) {  /* save wavefield every *jsnap* time steps */
	if(! sf_getint("jsnap",&jsnap)) jsnap=nt;
    }
    if(back) {
        shft = (nt-1)%jsnap;
        sf_warning("For backward extrapolation, make sure nbell(%d)=0",nbell);
    } else shft = 0;

    /*------------------------------------------------------------*/
    /* expand domain for FD operators and ABC                     */
    /*------------------------------------------------------------*/
    if( !sf_getint("nb",&nb)) nb=NOP;

    fdm=fdutil3d_init(verb,fsrf,az,ax,ay,nb,1);
    if(nbell) fdbell3d_init(nbell);

    sf_setn(az,fdm->nzpad); sf_seto(az,fdm->ozpad); if(verb) sf_raxa(az);
    sf_setn(ax,fdm->nxpad); sf_seto(ax,fdm->oxpad); if(verb) sf_raxa(ax);
    sf_setn(ay,fdm->nypad); sf_seto(ay,fdm->oypad); if(verb) sf_raxa(ay);

    /*------------------------------------------------------------*/
    /* 3D vector components                                       */
    /*------------------------------------------------------------*/
    nc=3;
    ac=sf_maxa(nc,0,1); /* output 3 cartesian components */

    /*------------------------------------------------------------*/
    /* setup output data header                                   */
    /*------------------------------------------------------------*/
    sf_settype(Fdat,SF_COMPLEX);
    sf_oaxa(Fdat,arx,1);
    sf_oaxa(Fdat,ary,2);
    sf_oaxa(Fdat,ac,3);

    sf_setn(at,nt/jdata);
    sf_setd(at,dt*jdata);
    sf_oaxa(Fdat,at,4);

    /* setup output wavefield header */
    if(snap) {
	if(!sf_getint  ("nqz",&nqz)) nqz=sf_n(az);
	if(!sf_getint  ("nqx",&nqx)) nqx=sf_n(ax);
	if(!sf_getint  ("nqy",&nqy)) nqy=sf_n(ay);

	if(!sf_getfloat("oqz",&oqz)) oqz=sf_o(az);
	if(!sf_getfloat("oqx",&oqx)) oqx=sf_o(ax);
	if(!sf_getfloat("oqy",&oqy)) oqy=sf_o(ay);

	dqz=sf_d(az);
	dqx=sf_d(ax);
	dqy=sf_d(ay);

	acz = sf_maxa(nqz,oqz,dqz); sf_raxa(acz);
	acx = sf_maxa(nqx,oqx,dqx); sf_raxa(acx);
	acy = sf_maxa(nqy,oqy,dqy); sf_raxa(acy);

	uc=sf_complexalloc3(sf_n(acz),sf_n(acx),sf_n(acy));

	ntsnap=0; /* ntsnap = it/jsnap+1; */
	for(it=0; it<nt; it++) {
	    if(it%jsnap==0) ntsnap++;
	}
	sf_setn(at,  ntsnap);
	sf_setd(at,dt*jsnap);
	if(verb) sf_raxa(at);

        sf_settype(Fwfp,SF_COMPLEX);
	sf_oaxa(Fwfp,acz,1);
	sf_oaxa(Fwfp,acx,2);
	sf_oaxa(Fwfp,acy,3);
	sf_oaxa(Fwfp,ac, 4);
	sf_oaxa(Fwfp,at, 5);

        sf_settype(Fwfs,SF_COMPLEX);
	sf_oaxa(Fwfs,acz,1);
	sf_oaxa(Fwfs,acx,2);
	sf_oaxa(Fwfs,acy,3);
	sf_oaxa(Fwfs,ac, 4);
	sf_oaxa(Fwfs,at, 5);
    }

    /*------------------------------------------------------------*/
    /* source and data array                                      */
    /*------------------------------------------------------------*/
    ww=sf_complexalloc3(ns,nc,nt); /* Fast axis: n_sou > n_comp > n_time */
    sf_complexread(ww[0][0],nt*nc*ns,Fwav);

    dd=sf_complexalloc2(nr,nc);

    /*------------------------------------------------------------*/
    /* setup source/receiver coordinates                          */
    /*------------------------------------------------------------*/
    ss = (pt3d*) sf_alloc(ns,sizeof(*ss)); 
    rr = (pt3d*) sf_alloc(nr,sizeof(*rr)); 

    pt3dread1(Fsou,ss,ns,3); /* read (x,y,z) coordinates */
    pt3dread1(Frec,rr,nr,3); /* read (x,y,z) coordinates */

    /* calculate 3d linear interpolation coef for sou & rec */
    cs = lint3d_make(ns,ss,fdm);
    cr = lint3d_make(nr,rr,fdm);

    /*------------------------------------------------------------*/
    /* allocate and initialize wavefield arrays                   */
    /*------------------------------------------------------------*/
    /* z-component */
    uoz=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uoz_p=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uoz_s=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    /*upz=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);*/

    /* x-component */
    uox=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uox_p=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uox_s=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    /*upx=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);*/

    /* y-component */
    uoy=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uoy_p=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    uoy_s=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);
    /*upy=sf_complexalloc3(fdm->nzpad,fdm->nxpad,fdm->nypad);*/

    /* wavefield vector */
    uo = (sf_complex**) sf_alloc(3,sizeof(sf_complex*));
    uo[0] = uox[0][0]; uo[1] = uoy[0][0]; uo[2] = uoz[0][0];
    uo_p = (sf_complex**) sf_alloc(3,sizeof(sf_complex*));
    uo_p[0] = uox_p[0][0]; uo_p[1] = uoy_p[0][0]; uo_p[2] = uoz_p[0][0];
    uo_s = (sf_complex**) sf_alloc(3,sizeof(sf_complex*));
    uo_s[0] = uox_s[0][0]; uo_s[1] = uoy_s[0][0]; uo_s[2] = uoz_s[0][0];
    /*up = (sf_complex**) sf_alloc(3,sizeof(sf_complex*));*/
    /*up[0] = upx[0][0]; up[1] = upy[0][0]; up[2] = upz[0][0];*/

    /* initialize fft and lrk */
    dft = dft3d_init(1,false,false,fdm);
    nxyz= fdm->nypad*fdm->nxpad*fdm->nzpad;
    nk  = dft->nky  *dft->nkx  *dft->nkz;

    /*------------------------------------------------------------*/ 
    /* allocation I/O arrays                                      */
    /*------------------------------------------------------------*/ 
    n2s_p = sf_intalloc(9);
    sf_intread(n2s_p,9,Frkp);
    clr_p = clr3d_make2(n2s_p,fdm);

    n2s_s = sf_intalloc(9);
    sf_intread(n2s_s,9,Frks);
    clr_s = clr3d_make2(n2s_s,fdm);

    if (clr_p->n2_max > clr_s->n2_max) clr3d_init(fdm,dft,clr_p);
    else clr3d_init(fdm,dft,clr_s);

    /* check the dimension */
    if (!sf_histint(Fltp,"n1",&ntmp) || ntmp != nxyz)          sf_error("Need n1=%d in left",nxyz);
    if (!sf_histint(Fltp,"n2",&ntmp) || ntmp != clr_p->n2_sum) sf_error("Need n2=%d in left",clr_p->n2_sum);
    if (!sf_histint(Frtp,"n1",&ntmp) || ntmp != nk)            sf_error("Need n1=%d in right",nk);
    if (!sf_histint(Frtp,"n2",&ntmp) || ntmp != clr_p->n2_sum) sf_error("Need n2=%d in right",clr_p->n2_sum);
  
    lt_p = sf_complexalloc2(nxyz,clr_p->n2_sum); 
    rt_p = sf_complexalloc2(nk  ,clr_p->n2_sum); 
    sf_complexread(lt_p[0],nxyz*clr_p->n2_sum,Fltp);
    sf_complexread(rt_p[0],nk  *clr_p->n2_sum,Frtp);

    if (!sf_histint(Flts,"n1",&ntmp) || ntmp != nxyz)          sf_error("Need n1=%d in left",nxyz);
    if (!sf_histint(Flts,"n2",&ntmp) || ntmp != clr_s->n2_sum) sf_error("Need n2=%d in left",clr_s->n2_sum);
    if (!sf_histint(Frts,"n1",&ntmp) || ntmp != nk)            sf_error("Need n1=%d in right",nk);
    if (!sf_histint(Frts,"n2",&ntmp) || ntmp != clr_s->n2_sum) sf_error("Need n2=%d in right",clr_s->n2_sum);

    lt_s = sf_complexalloc2(nxyz,clr_s->n2_sum); 
    rt_s = sf_complexalloc2(nk  ,clr_s->n2_sum); 
    sf_complexread(lt_s[0],nxyz*clr_s->n2_sum,Flts);
    sf_complexread(rt_s[0],nk  *clr_s->n2_sum,Frts);

    /* initialize to zero */
#ifdef _OPENMP
#pragma omp parallel for              \
    schedule(dynamic,1)               \
    private(iy,ix,iz)                 \
    shared(fdm,uoz,uox,uoy,uoz_p,uox_p,uoy_p,uoz_s,uox_s,uoy_s)
#endif
    for        (iy=0; iy<fdm->nypad; iy++) {
	for    (ix=0; ix<fdm->nxpad; ix++) {
	    for(iz=0; iz<fdm->nzpad; iz++) {
		uoz  [iy][ix][iz]=sf_cmplx(0.,0.); uox  [iy][ix][iz]=sf_cmplx(0.,0.); uoy  [iy][ix][iz]=sf_cmplx(0.,0.);
		uoz_p[iy][ix][iz]=sf_cmplx(0.,0.); uox_p[iy][ix][iz]=sf_cmplx(0.,0.); uoy_p[iy][ix][iz]=sf_cmplx(0.,0.);
		uoz_s[iy][ix][iz]=sf_cmplx(0.,0.); uox_s[iy][ix][iz]=sf_cmplx(0.,0.); uoy_s[iy][ix][iz]=sf_cmplx(0.,0.);
		/*upz[iy][ix][iz]=sf_cmplx(0.,0.); upx[iy][ix][iz]=sf_cmplx(0.,0.); upy[iy][ix][iz]=sf_cmplx(0.,0.);*/
	    }
	}
    }

    /*------------------------------------------------------------*/ 
    /*------------------------ MAIN LOOP -------------------------*/ 
    /*------------------------------------------------------------*/
    if(verb) fprintf(stderr,"\n");
    for (it=0; it<nt; it++) {
        if(verb) sf_warning("it=%d/%d;",it,nt); /*fprintf(stderr,"\b\b\b\b\b%d",it);*/

	/*------------------------------------------------------------*/
	/* apply lowrank matrix to wavefield vector                   */
        /*------------------------------------------------------------*/
        clr3d_apply(uo_p, uo, lt_p, rt_p, fdm, dft, clr_p);
        clr3d_apply(uo_s, uo, lt_s, rt_s, fdm, dft, clr_s);

	/*------------------------------------------------------------*/
        /* combine P and S wave modes                                 */
        /*------------------------------------------------------------*/
#ifdef _OPENMP
#pragma omp parallel for              \
        schedule(dynamic,1)               \
        private(iy,ix,iz)                 \
        shared(fdm,uoz,uox,uoy,uoz_p,uox_p,uoy_p,uoz_s,uox_s,uoy_s)
#endif
        for        (iy=0; iy<fdm->nypad; iy++) {
            for    (ix=0; ix<fdm->nxpad; ix++) {
                for(iz=0; iz<fdm->nzpad; iz++) {
                    uoz[iy][ix][iz] = uoz_p[iy][ix][iz] + uoz_s[iy][ix][iz];
                    uox[iy][ix][iz] = uox_p[iy][ix][iz] + uox_s[iy][ix][iz];
                    uoy[iy][ix][iz] = uoy_p[iy][ix][iz] + uoy_s[iy][ix][iz];
                    /*upz[iy][ix][iz]=sf_cmplx(0.,0.); upx[iy][ix][iz]=sf_cmplx(0.,0.); upy[iy][ix][iz]=sf_cmplx(0.,0.);*/
                }
            }
        }

	/*------------------------------------------------------------*/
	/* free surface */
	/*------------------------------------------------------------*/
	if(fsrf) { /* need to do something here */ }

        /*------------------------------------------------------------*/
	/* inject displacement source                                 */
	/*------------------------------------------------------------*/
        if(esou) {
            /* exploding force source */
            lint3d_expl_complex(uoz,uox,uoy,ww[it],cs);
        } else {
            if(nbell) {
                lint3d_bell_complex(uoz,ww[it][0],cs);
                lint3d_bell_complex(uox,ww[it][1],cs);
                lint3d_bell_complex(uoy,ww[it][2],cs);
            } else {
                lint3d_inject_complex(uoz,ww[it][0],cs);
                lint3d_inject_complex(uox,ww[it][1],cs);
                lint3d_inject_complex(uoy,ww[it][2],cs);
            }
        }

	/*------------------------------------------------------------*/
	/* cut wavefield and save */
	/*------------------------------------------------------------*/
        if(snap && (it-shft)%jsnap==0) {
            /* P wave */
            cut3d_complex(uoz_p,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfp);

            cut3d_complex(uox_p,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfp);

            cut3d_complex(uoy_p,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfp);

            /* S wave */
            cut3d_complex(uoz_s,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfs);

            cut3d_complex(uox_s,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfs);

            cut3d_complex(uoy_s,uc,fdm,acz,acx,acy);
            sf_complexwrite(uc[0][0],sf_n(acx)*sf_n(acy)*sf_n(acz),Fwfs);
        }

        lint3d_extract_complex(uoz,dd[0],cr);
        lint3d_extract_complex(uox,dd[1],cr);
        lint3d_extract_complex(uoy,dd[2],cr);
        if(it%jdata==0) sf_complexwrite(dd[0],nr*nc,Fdat);

    }
    if(verb) sf_warning(".");
    if(verb) fprintf(stderr,"\n");    
    
    /*------------------------------------------------------------*/
    /* deallocate arrays */
    
    free(dft);
    dft3d_finalize();
    free(clr_p); free(clr_s);
    clr3d_finalize();

    free(**ww); free(*ww); free(ww);
    free(ss);
    free(rr);
    free(*dd);  free(dd);

    free(n2s_p); free(n2s_s);
    free(*lt_p); free(lt_p); free(*rt_p); free(rt_p);
    free(*lt_s); free(lt_s); free(*rt_s); free(rt_s);

    free(**uoz  ); free(*uoz  ); free(uoz)  ;
    free(**uoz_p); free(*uoz_p); free(uoz_p);
    free(**uoz_s); free(*uoz_s); free(uoz_s);
    /*free(**upz); free(*upz); free(upz);*/
    free(uo); free(uo_p); free(uo_s);
    /*free(up);*/

    if (snap) {
       free(**uc);  free(*uc);  free(uc);    
    }

    /*------------------------------------------------------------*/


    exit (0);
}
Пример #12
0
int main(int argc, char* argv[]) 
{

    int ii, ix, iz, ix0, iz0, nin;
    int snx, snz, lnx, lnz;
    float sox, soz, lox, loz, sdx, sdz, ldx, ldz; 
    sf_file Fins, Fin, Fout;
    
    const char **filelist;
    sf_complex **large, **small;
    
    sf_axis lax, laz, sax, saz;
    
    sf_init(argc, argv);
    Fin = sf_input("in");
    Fout = sf_output("out");
    sf_settype(Fout,SF_COMPLEX);
            
    filelist = (const char**) sf_alloc ( (size_t)argc, sizeof(char*));
    
    nin=0;
    for (ii=1; ii< argc; ii++) {
	if (NULL != strchr(argv[ii],'=')) continue; 
	filelist[nin] = argv[ii];
	nin++;
    }
        
    if (0==nin) sf_error ("no input");
        
    laz = sf_iaxa(Fin, 1); lnz = sf_n(laz); ldz = sf_d(laz); loz = sf_o(laz);
    lax = sf_iaxa(Fin, 2); lnx = sf_n(lax); ldx = sf_d(lax); lox = sf_o(lax);
    
    sf_oaxa(Fout, laz, 1); 
    sf_oaxa(Fout, lax, 2);

    large = sf_complexalloc2(lnz, lnx);
    
    for (ix=0; ix<lnx; ix++)
	for (iz=0; iz<lnz; iz++)
	  large[ix][iz] = sf_cmplx(0.0,0.0);

    for (ii=0; ii <nin; ii++) {
	Fins = sf_input(filelist[ii]);
	saz = sf_iaxa(Fins, 1); snz = sf_n(saz); sdz = sf_d(saz); soz = sf_o(saz);
	sax = sf_iaxa(Fins, 2); snx = sf_n(sax); sdx = sf_d(sax); sox = sf_o(sax);
	
	if (sox < lox || sox+(snx-1)*sdx > lox+(lnx-1)*ldx ) sf_error("ox setting error !");
	if (soz < loz || soz+(snz-1)*sdz > loz+(lnz-1)*ldz ) sf_error("oz setting error !"); 
	if (sdx != ldx || sdz != ldz ) sf_error("d1, d2 setting error !");

	small =sf_complexalloc2(snz, snx);
	sf_complexread(small[0], snx*snz, Fins);

	ix0 = (int) ((sox - lox)/ldx +0.5 );
	iz0 = (int) ((soz - loz)/ldz +0.5 );

	for (ix=0; ix<snx; ix++) {
	    for (iz=0; iz<snz; iz++) {
		large[ix+ix0][iz+iz0] += small[ix][iz];
	    }
	}

	free(*small);
	free(small);
	sf_fileclose(Fins);
		
    }

    for (ix=0; ix<lnx; ix++) 
    sf_complexwrite(large[ix], lnz, Fout);

    exit(0);

}
Пример #13
0
void mexFunction(int nlhs, mxArray *plhs[], 
		 int nrhs, const mxArray *prhs[])
{
    int taglen, status, argc=2, i, ndim, len;
    const int *dim=NULL;
    size_t nbuf = BUFSIZ, nd, j;
    char *tag=NULL, *argv[] = {"matlab","-"}, *par=NULL, *filename=NULL;
    double *dr=NULL, *di=NULL;
    float *p=NULL;
    sf_complex *c=NULL;
    char buf[BUFSIZ], key[5];
    bool same;
    FILE *file2=NULL;
    sf_file file=NULL;
    
    /* Check for proper number of arguments. */
    if (nrhs < 2 || nrhs > 3) mexErrMsgTxt("Two or three inputs required.");

    /* Second input must be a string. */
    if (!mxIsChar(prhs[1]))
	mexErrMsgTxt("Second input must be a string.");

    /* Second input must be a row vector. */
    if (mxGetM(prhs[1]) != 1)
	mexErrMsgTxt("Second input must be a row vector.");

    /* Get the length of the input string. */
    taglen = mxGetN(prhs[1]) + 1;

    /* Allocate memory for input string. */
    tag = mxCalloc(taglen, sizeof(char));

    /* Copy the string data from prhs[1] into a C string. */
    status = mxGetString(prhs[1], tag, taglen);
    if (status != 0) 
	mexWarnMsgTxt("Not enough space. String is truncated.");

    if (3 == nrhs) {
        /* Input 3 must be a string. */
	if (!mxIsChar(prhs[2]))
	    mexErrMsgTxt("Input 3 must be a string.");

	/* Input 3 must be a row vector. */
	if (mxGetM(prhs[2]) != 1)
	    mexErrMsgTxt("Input 3 must be a row vector.");
	
	/* Get the length of the input string. */
	len = mxGetN(prhs[2]) + 1;
	
	/* Allocate memory for input string. */
	par = mxCalloc(len, sizeof(char));

	/* Copy the string data from prhs[2] into a C string. */
	status = mxGetString(prhs[2], par, len);
	if (status != 0) 
	    mexWarnMsgTxt("Not enough space. String is truncated.");

	same = (0 == (strncmp(par,"same",4)));
    } else {
	same = false;
    }

    sf_init(argc,argv);

    if (same) {
	file = sf_input(tag);
	filename = sf_histstring(file,"in");
	sf_fileclose(file);

	if (NULL == filename) mexErrMsgTxt("No in= in file.");
	file2 = fopen(filename,"ab");
	if (NULL == file2) 
	    mexErrMsgTxt("Could not open binary file for writing.");
    } else {
	file = sf_output(tag);
	file2 = NULL;
    }

    /* Input 1 must be a number. */
    if (!mxIsDouble(prhs[0])) mexErrMsgTxt("First input must be double.");

    /* get data dimensions */
    ndim=mxGetNumberOfDimensions(prhs[0]);
    dim=mxGetDimensions(prhs[0]);

    /* get data size */
    nd = mxGetNumberOfElements(prhs[0]);

    if (!same) {
	sf_setformat(file,mxIsComplex(prhs[0])?"native_complex":"native_float");

	/* Output */
	for (i=0; i < ndim; i++) {
	    sprintf(key,"n%d",i+1);
	    sf_putint(file,key,dim[i]);
	}
    }
    
    if (mxIsComplex(prhs[0])) {
	/* complex data */
	c = (sf_complex*) buf;

	dr = mxGetPr(prhs[0]);

	/* pointer to imaginary part */
	di = mxGetPi(prhs[0]);
	
	for (j=0, nbuf /= sizeof(sf_complex); nd > 0; nd -= nbuf) {
	    if (nbuf > nd) nbuf=nd;
	    
	    for (i=0; i < nbuf; i++, j++) {
		c[i] = sf_cmplx((float) dr[j],(float) di[j]);
	    }
	    
	    if (same) {
		if (nbuf != fwrite(c,sizeof(sf_complex),nbuf,file2)) 
		    mexWarnMsgTxt("Writing problems.");
	    } else {
		sf_complexwrite(c,nbuf,file);
	    }
	}

    } else { 
	/* real data */
	p = (float*) buf;

	dr = mxGetPr(prhs[0]);

	for (j=0, nbuf /= sizeof(float); nd > 0; nd -= nbuf) {
	    if (nbuf > nd) nbuf=nd;
	    
	    for (i=0; i < nbuf; i++, j++) {
		p[i] = (float) dr[j];
	    }
	    
	    if (same) {
		if (nbuf != fwrite(p,sizeof(float),nbuf,file2)) 
		    mexWarnMsgTxt("Writing problems.");
	    } else {
		sf_floatwrite(p,nbuf,file);
	    }
	}
    } 

    if (same) {
	fclose(file2);
    } else {
	sf_fileclose(file);
    }
}
Пример #14
0
int main(int argc, char* argv[])
{
    bool verb, adj, hessian;
    int n1, n2, nf, i;
    float df, of;
    sf_complex **img, *coe0, *coe, *dx, *dr;
    int iter, niter, cgiter, count;
    float rhsnorm, rhsnorm0, rhsnorm1, rate, gamma;
    char *what;
    sf_file in, out, image, coef, grad;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");

    if (NULL == (what = sf_getstring("what"))) what="tomo";
    /* what to compute (default tomography) */

    switch (what[0]) {
	case 'l': /* linear operator */

	    if (!sf_getbool("adj",&adj)) adj=false;
	    /* adjoint flag (for what=linear) */

	    /* read image */
	    if (NULL == sf_getstring("image"))
		sf_error("Need image image=");
	    image = sf_input("image");

	    if (!sf_histint(image,"n1",&n1)) sf_error("No n1 in image.");
	    if (!sf_histint(image,"n2",&n2)) sf_error("No n2 in image.");

	    if (!sf_histint(image,"n3",&nf)) sf_error("No n3 in image.");
	    if (!sf_histfloat(image,"o3",&of)) sf_error("No o3 in image.");
	    if (!sf_histfloat(image,"d3",&df)) sf_error("No d3 in image.");

	    img = NULL;

	    /* read coefficients */
	    if (NULL == sf_getstring("coef"))
		sf_error("Need coefficients coef=");
	    coef = sf_input("coef");

	    coe0 = sf_complexalloc(n1*n2*2);
	    sf_complexread(coe0,n1*n2*2,coef);
	    sf_fileclose(coef);
	    
	    /* allocate temporary memory */
	    dx  = sf_complexalloc(n1*n2*2);
	    dr  = sf_complexalloc(n1*n2*nf);

	    /* read input and write output header */
	    if (adj) {
		sf_complexread(dr,n1*n2*nf,in);

		sf_putint(out,"n3",2);
	    } else {
		sf_complexread(dx,n1*n2*2,in);

		sf_putint(out,"n3",nf);
	    }

	    /* initialize operator */
	    freqmig0_init(n1,n2, of,df,nf, img);

	    /* set operator */
	    freqmig0_set(coe0);

	    /* linear operator */
	    if (adj) {
		freqmig0_oper(true,false,n1*n2*2,n1*n2*nf,dx,dr);
	    } else {
		freqmig0_oper(false,false,n1*n2*2,n1*n2*nf,dx,dr);
	    }
	    	    
	    /* write output */
	    if (adj) {
		sf_complexwrite(dx,n1*n2*2,out);
	    } else {
		sf_complexwrite(dr,n1*n2*nf,out);
	    }

	    break;

	case 't': /* tomography */

	    /* read model dimension */
	    if (!sf_histint(in,"n1",&n1)) sf_error("No n1 in input.");
	    if (!sf_histint(in,"n2",&n2)) sf_error("No n2 in input.");
	    
	    /* read initial guess */
	    coe0 = sf_complexalloc(n1*n2*2);
	    sf_complexread(coe0,n1*n2*2,in);
	    
	    /* read image */
	    if (NULL == sf_getstring("image"))
		sf_error("Need image image=");
	    image = sf_input("image");

	    if (!sf_histint(image,"n3",&nf)) sf_error("No n3 in image.");
	    if (!sf_histfloat(image,"o3",&of)) sf_error("No o3 in image.");
	    if (!sf_histfloat(image,"d3",&df)) sf_error("No d3 in image.");

	    img = sf_complexalloc2(n1*n2,nf);
	    sf_complexread(img[0],n1*n2*nf,image);
	    sf_fileclose(image);

	    /* allocate temporary memory */
	    dx  = sf_complexalloc(n1*n2*2);
	    dr  = sf_complexalloc(n1*n2*nf);
	    coe = sf_complexalloc(n1*n2*2);

	    if (!sf_getint("niter",&niter)) niter=5;
	    /* number of inversion iterations */
	    
	    if (!sf_getint("cgiter",&cgiter)) cgiter=10;
	    /* number of conjugate-gradient iterations */

	    if (!sf_getbool("hessian",&hessian)) hessian=false;
	    /* if y, exact Hessian; n, Gauss-Newton */

	    if (!sf_getbool("verb",&verb)) verb=false;
	    /* verbosity flag */

	    /* output gradient at each iteration */
	    if (NULL != sf_getstring("grad")) {
		grad = sf_output("grad");
		sf_putint(grad,"n4",niter);
	    } else {
		grad = NULL;
	    }

	    /* initialize */
	    freqmig0_init(n1,n2, of,df,nf, img);

	    rhsnorm0 = freqmig0_cost(coe0,dr);
	    rhsnorm = rhsnorm0;
	    rhsnorm1 = rhsnorm;
	    rate = rhsnorm1/rhsnorm0;

	    sf_warning("L2 misfit after iteration 0 of %d: %g",niter,rate);

	    /* iterations over inversion */
	    for (iter=0; iter < niter; iter++) {

		/* set operator */
		freqmig0_set(coe0);

		/* solve update */
		sf_csolver(freqmig0_oper,sf_ccgstep,n1*n2*2,n1*n2*nf,dx,dr,cgiter,"verb",verb,"end");
		sf_ccgstep_close();

		/* output gradient */
		if (grad != NULL) sf_complexwrite(dx,n1*n2*2,grad);

		/* line search */
		gamma = 1.;
		for (count=0; count < 5; count++) {
	    
		    /* update */
		    for (i=0; i < n1*n2; i++) {
			coe[i]       = coe0[i]+gamma*sf_cmplx(crealf(dx[i]),0.);
			coe[n1*n2+i] = coe0[n1*n2+i]+gamma*sf_cmplx(crealf(dx[n1*n2+i]),0.);
		    }

		    /* check cost */
		    rhsnorm = freqmig0_cost(coe,dr);
		    rate = rhsnorm/rhsnorm1;
	    
		    if (rate < 1.) {
			for (i=0; i < n1*n2; i++) {
			    coe0[i] = coe[i];
			    coe0[n1*n2+i] = coe[n1*n2+i];
			}
		
			rhsnorm1 = rhsnorm;
			rate = rhsnorm1/rhsnorm0;
			break;
		    }

		    gamma *= 0.5;
		}

		if (count == 5) {
		    sf_warning("Line-search failure at iteration %d of %d.",iter+1,niter);
		    break;
		}

		sf_warning("L2 misfit after iteration %d of %d: %g (line-search %d)",iter+1,niter,rate,count);
	    }

	    /* write output */
	    sf_complexwrite(coe0,n1*n2*2,out);

	    /* clean-up */
	    freqmig0_close();
	    free(dx); free(dr);

	    break;
    }

    exit(0);
}
Пример #15
0
int main(int argc, char* argv[])
{
    bool inv, shot;
    map4 *map;
    int iw, nw, ih, nh, ik, nk, ib, nb, *fold;
    float dw, dh, dk, w0, h0, k0, w, h, k, eps, db, b, sinb, cosb, xi;
    sf_complex *slice, *slice2, *sum, sample, tshift, xshift; 
    float *hstr, *dt, *dx, *ds;
    sf_file in, out;
    
    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");
    
    if (!sf_getbool("inv",&inv)) inv=true;
    /* inversion flag */

    if (!sf_getbool("shot",&shot)) shot=false;
    /* if shot gathers instead of midpoint gathers */

    if (SF_COMPLEX != sf_gettype(in)) sf_error("Need complex input");
    if (!sf_histint(in,"n1",&nh)) sf_error("No n1= in input");
    if (!sf_histint(in,"n2",&nw)) sf_error("No n2= in input");
    if (!sf_histint(in,"n3",&nk)) sf_error("No n3= in input");

    if (!sf_histfloat(in,"d1",&dh)) sf_error("No d1= in input");
    if (!sf_histfloat(in,"d2",&dw)) sf_error("No d2= in input");
    if (!sf_histfloat(in,"d3",&dk)) sf_error("No d3= in input");

    if (!sf_histfloat(in,"o1",&h0)) sf_error("No o1= in input");
    if (!sf_histfloat(in,"o2",&w0)) sf_error("No o2= in input");
    if (!sf_histfloat(in,"o3",&k0)) sf_error("No o3= in input");

    dk *= 2*SF_PI;
    k0 *= 2*SF_PI;

    dw *= 2*SF_PI;
    w0 *= 2*SF_PI;

    if (!sf_getfloat("eps",&eps)) eps=0.01;
    /* stretch regularization */

    slice  = sf_complexalloc(nh);
    hstr   = sf_floatalloc(nh);
    slice2 = sf_complexalloc(nh);

    sum  = sf_complexalloc(nh);
    fold = sf_intalloc(nh);

    if (!sf_getint("nb",&nb)) nb=85;   /* number of angles */
    if (!sf_getfloat("db",&db)) db=1;   /* angle increment */
    db *= SF_PI/180;

    if (!sf_getfloat("xi",&xi)) xi=1;   /* continuation paremeter */

    map = (map4*) sf_alloc(nb,sizeof(map4));
    dt = sf_floatalloc(nb);
    dx = sf_floatalloc(nb);
    ds = shot? sf_floatalloc(nb):NULL;

    /* precompute things */
    for (ib=0; ib < nb; ib++) {
	b = (ib+1)*db;
	sinb = sinf(b);
	cosb = sqrtf(1.0f-xi*sinb*sinb);

	dt[ib] = logf(cosb);

	for (ih=0; ih < nh; ih++) {
	    h = h0 + ih*dh;

	    if (inv) {
		hstr[ih] = h*cosb;
	    } else {
		hstr[ih] = h/cosb;
	    }
	}

	if (inv) {
	    dx[ib]=xi*sinb;
	} else {
	    dx[ib]=xi*sinb/cosb;
	}

	if (shot) {
	    if (inv) {
		ds[ib] = 1.0f-cosb;
	    } else {
		ds[ib] = 1.0f-1.0f/cosb;
	    }
	}

	map[ib] = stretch4_init (nh, h0, dh, nh, eps);
	stretch4_define (map[ib],hstr);
    }	
	
    for (ik=0; ik < nk; ik++) {
	k = k0+ik*dk;   
	sf_warning("wavenumber %d of %d;",ik+1,nk);

	for (iw=0; iw < nw; iw++) {
	    w = w0+iw*dw;

	    sf_complexread(slice,nh,in);

	    for (ih=0; ih < nh; ih++) {
		sum[ih] = slice[ih];
		fold[ih] = 1;
	    }
	
	    for (ib=0; ib < nb; ib++) {
		b = w*dt[ib];
		sinb = sinf(b);
		cosb = SF_SIG(cosf(b))*sqrtf(1.0f-xi*sinb*sinb);

		tshift = sf_cmplx(cosb,-sinb);

		if (inv) {
		    cstretch4_apply  (map[ib],slice,slice2);
		} else {
		    cstretch4_invert (map[ib],slice2,slice);
		}

		for (ih=0; ih < nh; ih++) {
		    h = h0 + ih*dh;

		    if (shot) {
			b = k*h*ds[ib];
			sinb = sinf(b);
			cosb = SF_SIG(cosf(b))*sqrtf(1.0f-xi*sinb*sinb);

			xshift = tshift*sf_cmplx(cosb,sinb);
		    } else {
			xshift = tshift;
		    }
		    
		    sample = slice2[ih];

		    if (crealf(sample) != 0.0f || 
			cimagf(sample) != 0.0f) {
			sum[ih]  += sample*xshift*2.0f*cosf(k*h*dx[ib]);
			fold[ih] += 2;
		    }
		} /* ih */
	    } /* ib */
	
	    for (ih=0; ih < nh; ih++) {
		if (fold[ih] > 1) sum[ih] /= fold[ih];
	    }
	    
	    sf_complexwrite(sum,nh,out);
	} /* iw */
    } /* ik */
    sf_warning(".");
    
    exit(0);
}
Пример #16
0
int main(int argc, char* argv[])
{
    int dim, n[SF_MAX_DIM], i, j, s;
    float **der, **vel;
    float o[SF_MAX_DIM], d[SF_MAX_DIM], t0, shift, source, *t, dist;
    char key[6];
    sf_complex *P, *Q, **beam;
    sf_file in, deriv, out;
    
    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");
    
    /* read input dimension */
    dim = sf_filedims(in,n);

    if (dim > 2) sf_error("Only works for 2D.");

    for (i=0; i < dim; i++) {
	sprintf(key,"d%d",i+1);
	if (!sf_histfloat(in,key,d+i)) sf_error("No %s= in input.",key);
	sprintf(key,"o%d",i+1);
	if (!sf_histfloat(in,key,o+i)) o[i]=0.;
    }

    if (!sf_getfloat("t0",&t0)) t0=0.;
    /* time origin at source */
    
    if (!sf_getfloat("shift",&shift)) shift=1.;
    /* complex source shift */

    if (!sf_getfloat("source",&source)) source=o[1]+(n[1]-1)/2*d[1];
    /* source location */

    /* project source to grid point */
    s = (source-o[1])/d[1];
    
    /* read velocity model */
    vel = sf_floatalloc2(n[0],n[1]);
    sf_floatread(vel[0],n[0]*n[1],in);
    
    /* read derivative file */
    der = sf_floatalloc2(n[0],n[1]);
    if (NULL != sf_getstring("deriv")) {
	deriv = sf_input("deriv");
	sf_floatread(der[0],n[0]*n[1],deriv);
	sf_fileclose(deriv);
    } else {
	deriv = NULL;

	/* use finite difference for derivative if available */
	if (0 < s && s < n[1]-1) {
	    for (i=0; i < n[0]; i++)
		der[s][i] = (vel[s+1][i]-2*vel[s][i]+vel[s-1][i])/(d[1]*d[1]);
	} else {
	    for (i=0; i < n[0]; i++)
		der[s][i] = 0.;
	}
    }
    
    /* write output header */
    sf_settype(out,SF_COMPLEX);

    /* allocate memory for temporary data */
    t  = sf_floatalloc(n[0]);
    P  = sf_complexalloc(n[0]);
    Q  = sf_complexalloc(n[0]);
    beam = sf_complexalloc2(n[0],n[1]);

    /* complex source initial condition */
    t[0] = 0.;
    P[0] = sf_cmplx(0.,1./vel[s][0]);
    Q[0] = sf_cmplx(shift,0.);

    /* dynamic ray tracing along central ray (4th order Runge-Kutta) */
    for (i=1; i<n[0]; i++) {
	t[i] = t[i-1]+d[0]/2./vel[s][i-1]+d[0]/(vel[s][i-1]+vel[s][i]);
#ifdef SF_HAS_COMPLEX_H
	Q[i] = (P[i-1]-der[s][i-1]*Q[i-1]*d[0]/(vel[s][i-1]*vel[s][i-1]*4))
	    *vel[s][i-1]*d[0]+Q[i-1];
	P[i] = -((1.5*der[s][i-1]+0.5*der[s][i])*Q[i-1]+(der[s][i-1]+der[s][i])/2*vel[s][i-1]*d[0]/2*P[i-1])
	    *d[0]/(vel[s][i-1]*vel[s][i-1]*2)+P[i-1];
#else
	Q[i] = sf_cadd(sf_crmul(sf_cadd(P[i-1],sf_crmul(Q[i-1],-der[s][i-1]*d[0]/(vel[s][i-1]*vel[s][i-1]*4)))
				,vel[s][i-1]*d[0]),Q[i-1]);
	P[i] = sf_cadd(sf_crmul(sf_cadd(sf_crmul(Q[i-1],-((1.5*der[s][i-1]+0.5*der[s][i]))),
					sf_crmul(P[i-1],(der[s][i-1]+der[s][i])/2*vel[s][i-1]*d[0]/2)),d[0]/(vel[s][i-1]*vel[s][i-1]*2)),P[i-1]);
#endif
    }

    /* Gaussian beam */
    for (j=0; j<n[1]; j++) {
	dist = (j-s)*d[1];
	
	for (i=0; i<n[0]; i++) {
#ifdef SF_HAS_COMPLEX_H
	    beam[j][i] = t0+t[i]+0.5*dist*dist*P[i]/Q[i];
#else
	    beam[j][i] = sf_cadd(sf_cmplx(t0+t[i],0.),sf_crmul(sf_cdiv(P[i],Q[i]),0.5*dist*dist));
#endif
	}
    }

    sf_complexwrite(beam[0],n[0]*n[1],out);

    exit(0);
}
Пример #17
0
int main(int argc, char* argv[])
{
    bool inv, dip, verb, time, decomp;
    int i, i1, n1, iw, nw, i2, n2, rect, niter, n12, nt, ip, np;
    char *label;
    float t, d1, w, w0, dw, p0, dp, p;
    sf_complex *trace, *kbsc, *sscc=NULL;
    sf_file in, out, basis;
	
    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");
	
    if (SF_COMPLEX != sf_gettype(in)) sf_error("Need complex input");
	
    if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input");
    if (!sf_histfloat(in,"d1",&d1)) d1=1.;
    label = sf_histstring(in,"label1");
	
    if (!sf_getbool("inv",&inv)) inv=false;
    /* if y, do inverse transform */
	
    if (!sf_getbool("verb",&verb)) verb = false;
    /* verbosity flag */
	
    if (!sf_getbool("dip",&dip)) dip = false;
    /* if y, do dip decomposition */

    if (!sf_getbool("time",&time)) time = false;
    /* if y, decompose in time */

    if (!sf_getbool("decompose",&decomp)) decomp = false;
    /* if y, output decomposition */
	
    if (NULL != sf_getstring("basis")) {
	basis = sf_output("basis");
    } else {
	basis = NULL;
    }
	
    if (!inv) {
	n2 = sf_leftsize(in,1);
	sf_shiftdim(in, out, 2);
		
	if (!sf_getint("rect",&rect)) rect=10;
	/* smoothing radius (in time, samples) */
	if (!sf_getint("niter",&niter)) niter=100;
	/* number of inversion iterations */
		
	if (dip) {
	    if (!sf_getint("np",&np)) sf_error("Need np=");
	    /* number of slopes */
			
	    if (!sf_getfloat("dp",&dp)) sf_error("Need dp=");
	    /* slope step */
			
	    if (!sf_getfloat("p0",&p0)) sf_error("Need p0=");
	    /* first slope */
			
	    sf_putint(out,"n2",np);
	    sf_putfloat(out,"d2",dp);
	    sf_putfloat(out,"o2",p0);
	    sf_putstring(out,"label2","Slope");
	    sf_putstring(out,"unit2","");
			
            if (!sf_histint(in,"n2",&nw)) nw=1;
	    if (!sf_histfloat(in,"d2",&dw)) dw=1.;
	    if (!sf_histfloat(in,"o2",&w0)) w0=0.;
	} else {
	    if (time) {
		if (!sf_histint  (in,"n1",&nw)) sf_error("No n1= in input");
		if (!sf_histfloat(in,"d1",&dw)) sf_error("No d1= in input");

		nw = 2*(nw-1);
		dw = 1./(nw*dw);

		if (!sf_histint  (in,"fft_n1",&nw)) sf_error("No fft_n1= in input");
		if (!sf_histfloat(in,"fft_o1",&w0)) sf_error("No fft_o1= in input");

		/* fix label */
		if (NULL != (label = sf_histstring(in,"fft_label1"))) {
		    sf_putstring(out,"label1",label);
		} else if (NULL != (label = sf_histstring(in,"label1"))) {
		    (void) sf_fft_label(1,label,out);
		}
	    } else {
		if (!sf_getint("nw",&nw)) nw = kiss_fft_next_fast_size(n1);
		/* number of frequencies */
		
		if (!sf_getfloat("dw",&dw)) dw = 1./(nw*d1);
		/* frequency step */
		
		if (!sf_getfloat("w0",&w0)) w0=-0.5/d1;
		/* first frequency */
			
		if (NULL != label && !sf_fft_label(2,label,out)) 
		    sf_putstring(out,"label2","Wavenumber");
	    }

	    sf_fft_unit(2,sf_histstring(in,"unit1"),out);

	    sf_putint(out,"n2",nw);
	    sf_putfloat(out,"d2",dw);
	    sf_putfloat(out,"o2",w0);

	    if (time) {
		dw = -dw;
		w0 = -w0;
	    }
	}
    } else {
	n2 = sf_leftsize(in,2);
		
	if (dip) {
	    if (!sf_histint(in,"n2",&np)) sf_error("No n2= in input");
	    if (!sf_histfloat(in,"d2",&dp)) sf_error("No d2= in input");
	    if (!sf_histfloat(in,"o2",&p0)) sf_error("No o2= in input");
			
            if (!sf_histint(in,"n2",&nw)) nw=1;
	    if (!sf_histfloat(in,"d3",&dw)) dw=1.;
	    if (!sf_histfloat(in,"o3",&w0)) w0=0.;
	} else {
	    if (!sf_histint(in,"n2",&nw)) sf_error("No n2= in input");
	    if (!sf_histfloat(in,"d2",&dw)) sf_error("No d2= in input");
	    if (!sf_histfloat(in,"o2",&w0)) sf_error("No o2= in input");
	}
		
	sf_unshiftdim(in, out, 2);
    }
	
    if (NULL != basis) {
	sf_shiftdim(in, basis, 2);
	if (dip) {
	    sf_putint(basis,"n2",np);
	    sf_putfloat(basis,"d2",dp);
	    sf_putfloat(basis,"o2",p0);
	    sf_putstring(basis,"label2","Slope");
	    sf_putstring(basis,"unit2","");
	} else {
	    sf_putint(basis,"n2",nw);
	    sf_putfloat(basis,"d2",dw);
	    sf_putfloat(basis,"o2",w0);
	    if (NULL != label && !sf_fft_label(2,label,basis)) 
		sf_putstring(basis,"label2","Wavenumber");
	    sf_fft_unit(2,sf_histstring(in,"unit1"),out);
	}
    }
    
    nt = dip? np:nw;
	
    n12 = nt*n1;
    dw *= 2.*SF_PI;
    w0 *= 2.*SF_PI;
	
    trace = sf_complexalloc(n1);
    kbsc = sf_complexalloc(n12);
    sscc = sf_complexalloc(n12);
    
    if (!dip) {
	/* basis functions */
	for (iw=0; iw < nw; iw++) {
	    w = w0 + iw*dw;
			
	    for (i1=0; i1 < n1; i1++) {
		t = i1*d1;
				
		kbsc[iw*n1+i1] = sf_cmplx(cosf(w*t),sinf(w*t));
	    }
	}
		
	if (NULL != basis) {
	    sf_complexwrite(kbsc,n12,basis);
	}
    }
	
    if (!inv) cmultidivn_init(nt, 1, n1, &n1, &rect, kbsc, (bool) (verb && (n2 < 500)));
	
    for (i2=0; i2 < n2; i2++) {
	sf_warning("slice %d of %d;",i2+1,n2);
		
	if (dip) {
	    w = w0 + (i2 % nw)*dw;
	    for (ip=0; ip < np; ip++) {
		p = -w*(p0 + ip*dp);
				
		for (i1=0; i1 < n1; i1++) {
		    t = i1*d1;
					
		    kbsc[ip*n1+i1] = sf_cmplx(cosf(p*t),sinf(p*t));
		}
	    }
			
	    if (NULL != basis) {
		sf_complexwrite(kbsc,n12,basis);
	    }
	}
		
	if (!inv) {
	    sf_complexread(trace,n1,in);
	    cmultidivn (trace,sscc,niter);

	    if (decomp) {
		for (iw=0; iw < nt; iw++) {
		    for (i1=0; i1 < n1; i1++) {
			i = iw*n1+i1;
					
#ifdef SF_HAS_COMPLEX_H
			sscc[i] *= kbsc[i];
#else
			sscc[i1] = sf_cmul(sscc[i],kbsc[i]);
#endif
		    }
		}
	    }

	    sf_complexwrite(sscc,n12,out);
	} else {
	    for (i1=0; i1 < n1; i1++) {
		trace[i1] = sf_cmplx(0.,0.);
	    }
	    sf_complexread(sscc,n12,in);
	    for (iw=0; iw < nt; iw++) {
		for (i1=0; i1 < n1; i1++) {
		    i = iw*n1+i1;
					
#ifdef SF_HAS_COMPLEX_H
		    trace[i1] += sscc[i]*kbsc[i];
#else
		    trace[i1] = sf_cadd(trace[i1],sf_cmul(sscc[i],kbsc[i]));
#endif
		}
	    }
	    sf_complexwrite(trace,n1,out);
	}
    }
    sf_warning(".");
	
    exit(0);
}
Пример #18
0
int main(int argc, char* argv[])
{
    bool verb,complx,sub,os;
    int it,iz,im,ik,ix,i,j;     /* index variables */
    int nt,nz,nx, m2, nk, nzx, nz2, nx2, nzx2, n2, pad1,nth;
    sf_complex c,old;
    int snap;

    /* I/O arrays*/
    sf_complex *ww,*curr,*prev,*cwave,*cwavem,**wave,**lt, **rt;
    float *rcurr,*rr;
    
    sf_file Fw,Fr,Fo;    /* I/O files */
    sf_axis at,az,ax;    /* cube axes */
    sf_file left, right;
    sf_file snaps;

    /*for tapering*/
    float dt,dx,dz,dkx,dkz,kx0,kz0,kx,kz,ktmp,kx_trs,kz_trs,thresh;
    float *ktp;
    int taper;

    sf_init(argc,argv);
    if(!sf_getbool("verb",&verb)) verb=false; /* verbosity */
    if(!sf_getbool("cmplx",&complx)) complx=true; /* outputs complex wavefield */
    if(!sf_getbool("os",&os)) os=true; /* one-step flag */
    if (os) {
      sf_warning("One-step wave extrapolation");
      if(!sf_getbool("sub",&sub)) sub=false; /* subtraction flag */
    } else {
      sf_warning("Two-step wave extrapolation");
      if(!sf_getbool("sub",&sub)) sub=true; /* subtraction flag */
    }
    if (!sf_getint("taper",&taper)) taper=0; /* tapering in the frequency domain */
    if (!sf_getfloat("thresh",&thresh)) thresh=0.92; /* tapering threshold */

    /* setup I/O files */
    Fw = sf_input ("in" );
    Fo = sf_output("out");
    Fr = sf_input ("ref");

    if (SF_COMPLEX != sf_gettype(Fw)) sf_error("Need complex input");
    if (SF_FLOAT != sf_gettype(Fr)) sf_error("Need float ref");

    if(complx)
	sf_settype(Fo,SF_COMPLEX);
    else
	sf_settype(Fo,SF_FLOAT);

    /* Read/Write axes */
    at = sf_iaxa(Fw,1); nt = sf_n(at); dt = sf_d(at);
    az = sf_iaxa(Fr,1); nz = sf_n(az); dz = sf_d(az);
    ax = sf_iaxa(Fr,2); nx = sf_n(ax); dx = sf_d(ax);

    sf_oaxa(Fo,az,1); 
    sf_oaxa(Fo,ax,2); 

    if (!sf_getint("snap",&snap)) snap=0;
    /* interval for snapshots */

    if (snap > 0) {
	snaps = sf_output("snaps");
	/* (optional) snapshot file */
	
	sf_oaxa(snaps,az,1); 
	sf_oaxa(snaps,ax,2);
	sf_oaxa(snaps,at,3);

	sf_putint(snaps,"n3",nt/snap);
	sf_putfloat(snaps,"d3",dt*snap);
	sf_putfloat(snaps,"o3",0.);

        if(complx)
          sf_settype(snaps,SF_COMPLEX);
        else
          sf_settype(snaps,SF_FLOAT);
    } else {
	snaps = NULL;
    }
    
    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */

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

    nk = cfft2_init(pad1,nz,nx,&nz2,&nx2);

    nzx = nz*nx;
    nzx2 = nz2*nx2;

    /* propagator matrices */
    left = sf_input("left");
    right = sf_input("right");

    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");
    
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);
  
    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);

    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);

    sf_fileclose(left);
    sf_fileclose(right);

    /* read wavelet & reflectivity */
    ww=sf_complexalloc(nt);  
    sf_complexread(ww,nt ,Fw);

    rr=sf_floatalloc(nzx); 
    sf_floatread(rr,nzx,Fr);

    curr   = sf_complexalloc(nzx2);
    if (!os) prev = sf_complexalloc(nzx2);
    else prev = NULL;
    if(!complx) rcurr  = sf_floatalloc(nzx2);
    else rcurr=NULL;

    cwave  = sf_complexalloc(nk);
    cwavem = sf_complexalloc(nk);
    wave   = sf_complexalloc2(nzx2,m2);

    /*icfft2_allocate(cwavem);*/

    for (iz=0; iz < nzx2; iz++) {
	curr[iz] = sf_cmplx(0.,0.);
	if (!os) prev[iz] = sf_cmplx(0.,0.);
	if(!complx) rcurr[iz]= 0.;
    }

    if (taper!=0) {
      dkz = 1./(nz2*dz); kz0 = -0.5/dz;
      dkx = 1./(nx2*dx); kx0 = -0.5/dx;
      kx_trs = thresh*fabs(0.5/dx);
      kz_trs = thresh*fabs(0.5/dz);
      sf_warning("dkz=%f,dkx=%f,kz0=%f,kx0=%f",dkz,dkx,kz0,kx0);
      sf_warning("nk=%d,nkz=%d,nkx=%d",nk,nz2,nx2);
      sf_warning("Applying kz tapering below %f",kz_trs);
      sf_warning("Applying kx tapering below %f",kx_trs);
      ktp = sf_floatalloc(nk);
      /* constructing the tapering op */
      for (ix=0; ix < nx2; ix++) {
	kx = kx0+ix*dkx;
	for (iz=0; iz < nz2; iz++) {
	  kz = kz0+iz*dkz;
	  ktmp = 1.;
	  if (fabs(kx) > kx_trs)
	    ktmp *= (fabs(kx)>kx_trs)? powf((fabs(kx0)-fabs(kx)+kx_trs)/kx0,2) : 1.;
	  if (fabs(kz) > kz_trs)
	    ktmp *= (fabs(kz)>kz_trs)? powf((fabs(kz0)-fabs(kz)+kz_trs)/kz0,2) : 1.;
     	  ktp[iz+ix*nz2] = ktmp;
	}
      }
    }

    /* MAIN LOOP */
    for (it=0; it<nt; it++) {
	if(verb) sf_warning("it=%d;",it);

	/* matrix multiplication */
	cfft2(curr,cwave);

	for (im = 0; im < m2; im++) {
	    for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
		cwavem[ik] = cwave[ik]*rt[ik][im];
#else
		cwavem[ik] = sf_cmul(cwave[ik],rt[ik][im]); //complex multiplies complex
#endif
	    }
	    icfft2(wave[im],cwavem);
	}

	for (ix = 0; ix < nx; ix++) {
	    for (iz=0; iz < nz; iz++) {
	        i = iz+ix*nz;  /* original grid */
		j = iz+ix*nz2; /* padded grid */
#ifdef SF_HAS_COMPLEX_H
		c = ww[it] * rr[i]; // source term
#else
		c = sf_crmul(ww[it], rr[i]); // source term
#endif
		if (sub) c += curr[j];
		if (!os) {
		  old = curr[j];
#ifdef SF_HAS_COMPLEX_H
		  c += sub? (old-prev[j]) : -prev[j];
#else
		  c = sf_cadd(c,sub? sf_csub(old,prev[j]) : sf_cneg(prev[j]));
#endif
		  prev[j] = old;
		}
		for (im = 0; im < m2; im++) {
#ifdef SF_HAS_COMPLEX_H
		    c += lt[im][i]*wave[im][j];
#else
		    c += sf_cmul(lt[im][i], wave[im][j]);
#endif
		}

		curr[j] = c;
		if (!complx) rcurr[j] = crealf(c);

	    }

	    if (NULL != snaps && 0 == it%snap) {
              /* write wavefield snapshots */
	    if (complx)
              sf_complexwrite(curr+ix*nz2,nz,snaps);
            else
              sf_floatwrite(rcurr+ix*nz2,nz,snaps);
	    }
	}

	if (taper!=0) {
	  if (it%taper == 0) {
	    cfft2(curr,cwave);
	    for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
	      cwavem[ik] = cwave[ik]*ktp[ik];
#else
	      cwavem[ik] = sf_crmul(cwave[ik],ktp[ik]);
#endif
	    }
	    icfft2(curr,cwavem);
            if (!os) {
              cfft2(prev,cwave);
              for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
                cwavem[ik] = cwave[ik]*ktp[ik];
#else
                cwavem[ik] = sf_crmul(cwave[ik],ktp[ik]);
#endif
              }
              icfft2(prev,cwavem);
            }
	  }
	}

    }
    if(verb) sf_warning("."); 

    /* write final wavefield to output */
    for (ix = 0; ix < nx; ix++) {
      if (complx)
        sf_complexwrite(curr+ix*nz2,nz,Fo);
      else
        sf_floatwrite(rcurr+ix*nz2,nz,Fo);
    }

    cfft2_finalize();
    exit (0);
}
Пример #19
0
int main(int argc, char* argv[])
{
    bool inv, verb;
    int i1, n1, iw, nt, nw, i2, n2, rect0, niter, n12, n1w;
    int m[SF_MAX_DIM], *rect;
    float t, d1, w, w0, dw, mean=0.0f, alpha;
    float *trace, *kbsc, *mkbsc, *sscc, *mm, *ww;
    sf_complex *outp, *cbsc;
    sf_file in, out, mask, weight, basis;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");

    if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input");
    if (!sf_histfloat(in,"d1",&d1)) d1=1.;

    if (!sf_getbool("inv",&inv)) inv=false;
    /* if y, do inverse transform */

    if (!sf_getbool("verb",&verb)) verb = false;
    /* verbosity flag */

    if (NULL != sf_getstring("basis")) {
        basis = sf_output("basis");
        sf_settype(basis,SF_COMPLEX);
    } else {
        basis = NULL;
    }

    if (!inv) {
        if (!sf_getint("nw",&nw)) { /* number of frequencies */
            nt = 2*kiss_fft_next_fast_size((n1+1)/2);
            nw = nt/2+1;
            dw = 1./(nt*d1);
            w0 = 0.;
        } else {
            if (!sf_getfloat("dw",&dw)) {
                /* frequency step */
                nt = 2*kiss_fft_next_fast_size((n1+1)/2);
                dw = 1./(nt*d1);
            }
            if (!sf_getfloat("w0",&w0)) w0=0.;
            /* first frequency */
        }
        n2 = sf_leftsize(in,1);
        sf_shiftdim(in, out, 2);
        sf_putint(out,"n2",nw);
        sf_putfloat(out,"d2",dw);
        sf_putfloat(out,"o2",w0);
        sf_putstring(out,"label2","Frequency");
        sf_putstring(out,"unit2","Hz");
        sf_settype(out,SF_COMPLEX);

        if (!sf_getint("rect",&rect0)) rect0=10;
        /* smoothing radius (in time, samples) */
        if (!sf_getint("niter",&niter)) niter=100;
        /* number of inversion iterations */
        if (!sf_getfloat("alpha",&alpha)) alpha=0.;
        /* frequency adaptivity */

        for(i2=0; i2 < SF_MAX_DIM; i2 ++) {
            m[i2] = 1;
        }
        m[0] = n1;
    } else {
        n2 = sf_leftsize(in,2);
        if (!sf_histint(in,"n2",&nw)) sf_error("No n2= in input");
        if (!sf_histfloat(in,"d2",&dw)) sf_error("No d2= in input");
        if (!sf_histfloat(in,"o2",&w0)) sf_error("No o2= in input");
        sf_unshiftdim(in, out, 2);
        sf_settype(out,SF_FLOAT);
    }

    if (NULL != basis) {
        sf_shiftdim(in, basis, 2);
        sf_putint(basis,"n2",nw);
        sf_putfloat(basis,"d2",dw);
        sf_putfloat(basis,"o2",w0);
        sf_putstring(basis,"label2","Frequency");
        sf_putstring(basis,"unit2","Hz");
    }

    n1w = n1*nw;
    n12 = 2*n1w;
    dw *= 2.*SF_PI;
    w0 *= 2.*SF_PI;

    trace = sf_floatalloc(n1);
    kbsc    = sf_floatalloc(n12);
    outp = sf_complexalloc(n1w);
    cbsc = sf_complexalloc(n1w);

    rect = sf_intalloc(2*nw);
    for (iw=0; iw < nw; iw++) {
        rect[iw+nw] = rect[iw] = SF_MAX(1, (int) rect0/(1.0+alpha*iw/nw));
    }

    if (!inv) {
        sscc = sf_floatalloc(n12);
        nmultidivn_init(2*nw, 1, n1, m, rect, kbsc,
                        (bool) (verb && (n2 < 500)));
    } else {
        sscc = NULL;
    }

    if (NULL != sf_getstring("mask")) { /* data weight */
        mask = sf_input("mask");
        mm = sf_floatalloc(n1);
    } else {
        mask = NULL;
        mm = NULL;
    }

    if (NULL != sf_getstring("weight")) { /* model weight */
        weight = sf_input("weight");
        ww = sf_floatalloc(n1w);
    } else {
        weight = NULL;
        ww = NULL;
    }

    /* sin and cos basis */
    for (iw=0; iw < nw; iw++) {
        w = w0 + iw*dw;
        for (i1=0; i1 < n1; i1++) {
            if (0.==w) { /* zero frequency */
                kbsc[iw*n1+i1] = 0.;
            } else {
                t = i1*d1;
                kbsc[iw*n1+i1] = sinf(w*t);
            }
        }
    }
    for (iw=0; iw < nw; iw++) {
        w = w0 + iw*dw;
        for (i1=0; i1 < n1; i1++) {
            if (0.==w) { /* zero frequency */
                kbsc[(iw+nw)*n1+i1] = 0.5;
            } else {
                t = i1*d1;
                kbsc[(iw+nw)*n1+i1] = cosf(w*t);
            }

            cbsc[iw*n1+i1] = sf_cmplx(kbsc[(iw+nw)*n1+i1],
                                      kbsc[iw*n1+i1]);
        }
    }


    if (NULL != mm || NULL != ww) {
        mkbsc = sf_floatalloc(n12);
        for (i1=0; i1 < n12; i1++) {
            mkbsc[i1] = kbsc[i1];
        }
    } else {
        mkbsc = NULL;

        mean = 0.;
        for (i1=0; i1 < n12; i1++) {
            mean += kbsc[i1]*kbsc[i1];
        }
        mean = sqrtf (mean/(n12));
        for (i1=0; i1 < n12; i1++) {
            kbsc[i1] /= mean;
        }
    }

    for (i2=0; i2 < n2; i2++) {
        sf_warning("slice %d of %d;",i2+1,n2);

        if (NULL != basis) sf_complexwrite(cbsc,n1w,basis);

        if (NULL != mm || NULL != ww) {
            for (i1=0; i1 < n12; i1++) {
                kbsc[i1] = mkbsc[i1];
            }

            if (NULL != mm) {
                sf_floatread(mm,n1,mask);
                for (iw=0; iw < 2*nw; iw++) {
                    for (i1=0; i1 < n1; i1++) {
                        kbsc[iw*n1+i1] *= mm[i1];
                    }
                }
            }

            if (NULL != ww) {
                sf_floatread(ww,n1w,weight);
                for (iw=0; iw < nw; iw++) {
                    for (i1=0; i1 < n1; i1++) {
                        kbsc[iw*n1+i1]      *= ww[iw*n1+i1];
                        kbsc[(iw+nw)*n1+i1] *= ww[iw*n1+i1];
                    }
                }
            }

            mean = 0.;
            for (i1=0; i1 < n12; i1++) {
                mean += kbsc[i1]*kbsc[i1];
            }
            mean = sqrtf (mean/(n12));
            for (i1=0; i1 < n12; i1++) {
                kbsc[i1] /= mean;
            }
        }

        if (!inv) {
            sf_floatread(trace,n1,in);
            if (NULL != mm) {
                for (i1=0; i1 < n1; i1++) {
                    trace[i1] *= mm[i1];
                }
            }

            for(i1=0; i1 < n1; i1++) {
                trace[i1] /= mean;
            }
            nmultidivn (trace,sscc,niter);
            for (iw=0; iw < nw; iw++) {
                for (i1=0; i1 < n1; i1++) {
                    outp[iw*n1+i1] = sf_cmplx(sscc[(iw+nw)*n1+i1],
                                              sscc[iw*n1+i1]);
                }
            }

            if (NULL != ww) {
                for (i1=0; i1 < n1w; i1++) {
#ifdef SF_HAS_COMPLEX_H
                    outp[i1] *= ww[i1];
#else
                    outp[i1] = sf_crmul(outp[i1],ww[i1]);
#endif
                }
            }

            sf_complexwrite(outp,n1w,out);
        } else {
            for (i1=0; i1 < n1; i1++) {
                trace[i1] = 0.;
            }
            sf_complexread(outp,n1w,in);
            for (iw=0; iw < nw; iw++) {
                for (i1=0; i1 < n1; i1++) {
                    trace[i1] += crealf(outp[iw*n1+i1])*kbsc[(iw+nw)*n1+i1]
                                 *mean+cimagf(outp[iw*n1+i1])*kbsc[iw*n1+i1]*mean;
                    if (NULL != mm) trace[i1] *= mm[i1];
                }
            }
            sf_floatwrite(trace,n1,out);
        }
    }
    sf_warning(".");

    exit(0);
}
Пример #20
0
int main(int argc, char* argv[])
{
    bool verb, save, load;
    int npml, pad1, pad2, n1, n2; 
    int ih, nh, is, ns, iw, nw, i, j;
    SuiteSparse_long n, nz, *Ti, *Tj;
    float d1, d2, **vel, ****image, ****timage, dw, ow;
    double omega, *Tx, *Tz;
    SuiteSparse_long *Ap, *Ai, *Map;
    double *Ax, *Az, **Xx, **Xz, **Bx, **Bz;
    void *Symbolic, **Numeric;
    double Control[UMFPACK_CONTROL];
    sf_complex ***srce, ***recv;
    char *datapath, *insert, *append;
    size_t srclen, inslen;
    sf_file in, out, source, data, us, ur, timg;
    int uts, its, mts;
    sf_timer timer;
    char *order;

    sf_init(argc,argv);
    in  = sf_input("in");
    out = sf_output("out");

    if (!sf_getbool("verb",&verb)) verb=false;
    /* verbosity flag */

    if (verb)
	timer = sf_timer_init();
    else
	timer = NULL;

    if (!sf_getbool("save",&save)) save=false;
    /* save LU */

    if (!sf_getbool("load",&load)) load=false;
    /* load LU */

    if (save || load) {
	datapath = sf_histstring(in,"in");
	srclen = strlen(datapath);
	insert = sf_charalloc(6);
    } else {
	datapath = NULL;
	srclen = 0;
	insert = NULL;
	append = NULL;
    }

    if (!sf_getint("uts",&uts)) uts=0;
    /* number of OMP threads */

#ifdef _OPENMP
    mts = omp_get_max_threads();
#else
    mts = 1;
#endif

    uts = (uts < 1)? mts: uts;
    if (verb) sf_warning("Using %d out of %d threads.",uts,mts);

    if (!sf_getint("nh",&nh)) nh=0;
    /* horizontal space-lag */

    if (!sf_getint("npml",&npml)) npml=10;
    /* PML width */

    if (NULL == (order = sf_getstring("order"))) order="j";
    /* discretization scheme (default optimal 9-point) */

    fdprep_order(order);

    /* read model */
    if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input.");
    if (!sf_histint(in,"n2",&n2)) sf_error("No n2= in input.");

    if (!sf_histfloat(in,"d1",&d1)) sf_error("No d1= in input.");
    if (!sf_histfloat(in,"d2",&d2)) sf_error("No d2= in input.");

    vel = sf_floatalloc2(n1,n2);
    sf_floatread(vel[0],n1*n2,in);

    /* read source */
    if (NULL == sf_getstring("source"))
	sf_error("Need source=");
    source = sf_input("source");

    if (!sf_histint(source,"n3",&ns)) sf_error("No ns=.");
    if (!sf_histint(source,"n4",&nw)) sf_error("No nw=.");
    if (!sf_histfloat(source,"d4",&dw)) sf_error("No dw=.");
    if (!sf_histfloat(source,"o4",&ow)) sf_error("No ow=.");

    srce = sf_complexalloc3(n1,n2,ns);

    /* read receiver */
    if (NULL == sf_getstring("data"))
	sf_error("Need data=");
    data = sf_input("data");

    recv = sf_complexalloc3(n1,n2,ns);

    /* write output header */
    sf_putint(out,"n3",2*nh+1);
    sf_putfloat(out,"d3",d2);
    sf_putfloat(out,"o3",(float) -nh*d2);

    /* output source wavefield */
    if (NULL != sf_getstring("us")) {
	us = sf_output("us");
	
	sf_settype(us,SF_COMPLEX);
	sf_putint(us,"n3",ns);
	sf_putstring(us,"label3","Shot");
	sf_putstring(us,"unit3","");
	sf_putint(us,"n4",nw);
	sf_putfloat(us,"d4",dw);
	sf_putfloat(us,"o4",ow);
	sf_putstring(us,"label4","Frequency");
	sf_putstring(us,"unit4","Hz");
    } else {
	us = NULL;
    }

    /* output receiver wavefield */
    if (NULL != sf_getstring("ur")) {
	ur = sf_output("ur");
	
	sf_settype(ur,SF_COMPLEX);
	sf_putint(ur,"n3",ns);
	sf_putstring(ur,"label3","Shot");
	sf_putstring(ur,"unit3","");
	sf_putint(ur,"n4",nw);
	sf_putfloat(ur,"d4",dw);
	sf_putfloat(ur,"o4",ow);
	sf_putstring(ur,"label4","Frequency");
	sf_putstring(ur,"unit4","Hz");
    } else {
	ur = NULL;
    }

    /* output time-shift image derivative */
    if (NULL != sf_getstring("timg")) {
	timg = sf_output("timg");

	sf_putint(timg,"n3",2*nh+1);
	sf_putfloat(timg,"d3",d2);
	sf_putfloat(timg,"o3",(float) -nh*d2);

	timage = (float****) sf_alloc(uts,sizeof(float***));
	for (its=0; its < uts; its++) {
	    timage[its] = sf_floatalloc3(n1,n2,2*nh+1);
	}
    } else {
	timg = NULL;
	timage = NULL;
    }

    /* allocate temporary memory */    
    if (load) {
	Ti = NULL; Tj = NULL; Tx = NULL; Tz = NULL; 
	Ap = NULL; Ai = NULL; Map = NULL; Ax = NULL; Az = NULL;
    }
    
    Bx = (double**) sf_alloc(uts,sizeof(double*));
    Bz = (double**) sf_alloc(uts,sizeof(double*));
    Xx = (double**) sf_alloc(uts,sizeof(double*));
    Xz = (double**) sf_alloc(uts,sizeof(double*));

    image = (float****) sf_alloc(uts,sizeof(float***));
    for (its=0; its < uts; its++) {
	image[its] = sf_floatalloc3(n1,n2,2*nh+1);
    }
    
    Numeric = (void**) sf_alloc(uts,sizeof(void*));

    /* LU control */
    umfpack_zl_defaults (Control);
    Control [UMFPACK_IRSTEP] = 0;

    /* loop over frequency */
    for (iw=0; iw < nw; iw++) {
	omega = (double) 2.*SF_PI*(ow+iw*dw);

	/* PML padding */
	pad1 = n1+2*npml;
	pad2 = n2+2*npml;

	n  = fdprep_n (pad1,pad2);
	nz = fdprep_nz(pad1,pad2);

	if (!load) {
	    Ti = (SuiteSparse_long*) sf_alloc(nz,sizeof(SuiteSparse_long));
	    Tj = (SuiteSparse_long*) sf_alloc(nz,sizeof(SuiteSparse_long));
	    Tx = (double*) sf_alloc(nz,sizeof(double));
	    Tz = (double*) sf_alloc(nz,sizeof(double));
	    
	    Ap = (SuiteSparse_long*) sf_alloc(n+1,sizeof(SuiteSparse_long));
	    Ai = (SuiteSparse_long*) sf_alloc(nz,sizeof(SuiteSparse_long));
	    Map = (SuiteSparse_long*) sf_alloc(nz,sizeof(SuiteSparse_long));
	    
	    Ax = (double*) sf_alloc(nz,sizeof(double));
	    Az = (double*) sf_alloc(nz,sizeof(double));
	}
	for (its=0; its < uts; its++) {
	    Bx[its] = (double*) sf_alloc(n,sizeof(double));
	    Bz[its] = (double*) sf_alloc(n,sizeof(double));
	    Xx[its] = (double*) sf_alloc(n,sizeof(double));
	    Xz[its] = (double*) sf_alloc(n,sizeof(double));
	}

	if (verb) {
	    sf_warning("Frequency %d of %d.",iw+1,nw);
	    sf_timer_start(timer);
	}

	/* LU file (append _lu* after velocity file) */
	if (save || load) {
	    sprintf(insert,"_lu%d",iw);
	    inslen = strlen(insert);
	    
	    append = malloc(srclen+inslen+1);

	    memcpy(append,datapath,srclen-5);
	    memcpy(append+srclen-5,insert,inslen);
	    memcpy(append+srclen-5+inslen,datapath+srclen-5,5+1);
	}

	if (!load) {
	    /* assemble matrix */
	    fdprep(omega,
		   n1, n2, d1, d2, vel,
		   npml, pad1, pad2,
		   Ti, Tj, Tx, Tz);	    
	    
	    (void) umfpack_zl_triplet_to_col (n, n, nz, 
					      Ti, Tj, Tx, Tz, 
					      Ap, Ai, Ax, Az, Map);	    

	    /* LU */
	    (void) umfpack_zl_symbolic (n, n, 
					Ap, Ai, Ax, Az, 
					&Symbolic, Control, NULL);
	    
	    (void) umfpack_zl_numeric (Ap, Ai, Ax, Az, 
				       Symbolic, &Numeric[0], 
				       Control, NULL);
	    
	    /* save Numeric */
#ifdef _OPENMP
	    (void) umfpack_zl_save_numeric (Numeric[0], append);
	    
	    for (its=1; its < uts; its++) {
		(void) umfpack_zl_load_numeric (&Numeric[its], append);
	    }
	    
	    if (!save) {
		(void) remove (append);
		(void) remove ("numeric.umf");
	    }
#else
	    if (save) (void) umfpack_zl_save_numeric (Numeric[0], append);
#endif
	} else {
	    /* load Numeric */
	    for (its=0; its < uts; its++) {
		(void) umfpack_zl_load_numeric (&Numeric[its], append);
	    }
	}
	
	if (save || load) free(append);

	/* read source and data */
	sf_complexread(srce[0][0],n1*n2*ns,source);
	sf_complexread(recv[0][0],n1*n2*ns,data);

	/* loop over shots */
#ifdef _OPENMP
#pragma omp parallel for num_threads(uts) private(its,ih,j,i)
#endif
	for (is=0; is < ns; is++) {
#ifdef _OPENMP
	    its = omp_get_thread_num();
#else
	    its = 0;
#endif

	    /* source wavefield */
	    fdpad(npml,pad1,pad2, srce[is],Bx[its],Bz[its]);	    

	    (void) umfpack_zl_solve (UMFPACK_A, 
				     NULL, NULL, NULL, NULL, 
				     Xx[its], Xz[its], Bx[its], Bz[its], 
				     Numeric[its], Control, NULL);
	    
	    fdcut(npml,pad1,pad2, srce[is],Xx[its],Xz[its]);

	    /* receiver wavefield */
	    fdpad(npml,pad1,pad2, recv[is],Bx[its],Bz[its]);	    
	    
	    (void) umfpack_zl_solve (UMFPACK_At, 
				     NULL, NULL, NULL, NULL, 
				     Xx[its], Xz[its], Bx[its], Bz[its], 
				     Numeric[its], Control, NULL);
	    	    
	    fdcut(npml,pad1,pad2, recv[is],Xx[its],Xz[its]);

	    /* imaging condition */
	    for (ih=-nh; ih < nh+1; ih++) {
		for (j=0; j < n2; j++) {
		    for (i=0; i < n1; i++) {
			if (j-abs(ih) >= 0 && j+abs(ih) < n2) {
			    image[its][ih+nh][j][i] += crealf(conjf(srce[is][j-ih][i])*recv[is][j+ih][i]);
			    if (timg != NULL) timage[its][ih+nh][j][i] 
						  += crealf(2.*I*omega*conjf(srce[is][j-ih][i])*recv[is][j+ih][i]);
			}
		    }
		}
	    }
	}

	if (verb) {
	    sf_timer_stop (timer);
	    sf_warning("Finished in %g seconds.",sf_timer_get_diff_time(timer)/1.e3);
	}
	
	if (!load) (void) umfpack_zl_free_symbolic (&Symbolic);
	for (its=0; its < uts; its++) {
	    (void) umfpack_zl_free_numeric (&Numeric[its]);
	}

	if (!load) {
	    free(Ti); free(Tj); free(Tx); free(Tz);
	    free(Ap); free(Ai); free(Map);
	    free(Ax); free(Az);
	}
	for (its=0; its < uts; its++) {
	    free(Bx[its]); free(Bz[its]); free(Xx[its]); free(Xz[its]);
	}

	if (us != NULL) sf_complexwrite(srce[0][0],n1*n2*ns,us);
	if (ur != NULL) sf_complexwrite(recv[0][0],n1*n2*ns,ur);	
    }

#ifdef _OPENMP
#pragma omp parallel for num_threads(uts) private(j,i,its)
    for (ih=-nh; ih < nh+1; ih++) {
	for (j=0; j < n2; j++) {
	    for (i=0; i < n1; i++) {
		for (its=1; its < uts; its++) {
		    image[0][ih+nh][j][i] += image[its][ih+nh][j][i];
		    if (timg != NULL) timage[0][ih+nh][j][i] 
					  += timage[its][ih+nh][j][i];
		}
	    }
	}
    }
#endif
    
    sf_floatwrite(image[0][0][0],n1*n2*(2*nh+1),out);
    if (timg != NULL) sf_floatwrite(timage[0][0][0],n1*n2*(2*nh+1),timg);

    exit(0);
}
Пример #21
0
int main(int argc, char* argv[])
{
    sf_map4 mo;
    bool inv, each=true;
    int i, nt, n1, i2, n2, nw;
    float o1, d1, t0, dt, eps;
    sf_complex *ctrace, *ctrace2;
    float *trace, *str, *trace2;
    sf_file in, out, warp;

    sf_init(argc,argv);
    in = sf_input("in");
    out = sf_output("out");
    warp = sf_input("warp");

    if (!sf_getbool("inv",&inv)) inv=true;
    /* inversion flag */

    if (inv) {
	if (!sf_histint(in,"n1",&nt)) sf_error("No n1= in input");
	
	if (!sf_getint("n1",&n1)) n1=nt; /* output samples - for inv=y */
	if (!sf_getfloat("d1",&d1) && !sf_histfloat(in,"d1",&d1)) d1=1.;
	/*( d1=1 output sampling - for inv=y )*/
	if (!sf_getfloat("o1",&o1) && !sf_histfloat(in,"o1",&o1)) o1=0.;
	/*( o1=0 output origin - for inv=y )*/ 

	sf_putint(out,"n1",n1);
	sf_putfloat(out,"d1",d1);
	sf_putfloat(out,"o1",o1);
    } else {
	if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input");
	if (!sf_histfloat(in,"d1",&d1)) d1=1.;
	if (!sf_histfloat(in,"o1",&o1)) o1=0.;

	if (!sf_histint(warp,"n1",&nt)) sf_error("No n1= in warp");
	if (!sf_histfloat(warp,"d1",&dt)) dt=d1;
	if (!sf_histfloat(warp,"o1",&t0)) t0=o1;
	
	sf_putint(out,"n1",nt);
	sf_putfloat(out,"d1",dt);
	sf_putfloat(out,"o1",t0);
    }

    n2 = sf_leftsize(in,1);
    nw = sf_leftsize(warp,1);
    if (1 == nw) {
	each = false;
    } else if (n2 != nw) {
	sf_error("Need %d traces in warp, got %d",n2,nw);
    } 
    
    if (!sf_getfloat("eps",&eps)) eps=0.01;
    /* stretch regularization */

    trace = sf_floatalloc(nt);
    str = sf_floatalloc(nt);
    trace2 = sf_floatalloc(n1);

    mo = sf_stretch4_init (n1, o1, d1, nt, eps);

    if (SF_COMPLEX == sf_gettype(in)) {
	ctrace = sf_complexalloc(nt);
	ctrace2 = sf_complexalloc(n1);
    } else {
	ctrace = ctrace2 = NULL;
    }

    for (i2=0; i2 < n2; i2++) {
	if (each || 0==i2) {
	    sf_floatread(str,nt,warp);
	    sf_stretch4_define (mo,str);
	}

	if (inv) {
	    if (SF_COMPLEX == sf_gettype(in)) {
		sf_complexread(ctrace,nt,in);
		for (i=0; i < nt; i++) {
		    trace[i] = crealf(ctrace[i]);
		}
		sf_stretch4_apply (false,mo,trace,trace2);
		for (i=0; i < n1; i++) {
		    ctrace2[i] = sf_cmplx(trace2[i],0.0f);
		}
		for (i=0; i < nt; i++) {
		    trace[i] = cimagf(ctrace[i]);
		}
		sf_stretch4_apply (false,mo,trace,trace2);
		for (i=0; i < n1; i++) {
#ifdef SF_HAS_COMPLEX_H
		    ctrace2[i] += sf_cmplx(0.0f,trace2[i]);
#else
		    ctrace2[i] = sf_cadd(ctrace2[i],sf_cmplx(0.0f,trace2[i]));
#endif
		}
		sf_complexwrite (ctrace2,n1,out);
	    } else {
		sf_floatread(trace,nt,in);
		sf_stretch4_apply (false,mo,trace,trace2);
		sf_floatwrite (trace2,n1,out);
	    }
	} else {
	    if (SF_COMPLEX == sf_gettype(in)) {
		sf_complexread (ctrace2,n1,out);
		for (i=0; i < n1; i++) {
		    trace2[i] = crealf(ctrace2[i]);
		}
		sf_stretch4_invert (false,mo,trace,trace2);
		for (i=0; i < nt; i++) {
		    ctrace[i] = sf_cmplx(trace[i],0.0f);
		}
		for (i=0; i < n1; i++) {
		    trace2[i] = cimagf(ctrace2[i]);
		}
		sf_stretch4_invert (false,mo,trace,trace2);
		for (i=0; i < nt; i++) {
#ifdef SF_HAS_COMPLEX_H
		    ctrace[i] += sf_cmplx(0.0f,trace[i]);
#else
		    ctrace[i] = sf_cadd(ctrace[i],sf_cmplx(0.0f,trace[i]));
#endif
		}
		sf_complexwrite(ctrace,nt,in);
	    } else {
		sf_floatread(trace2,n1,in);
		sf_stretch4_invert (false,mo,trace,trace2);
		sf_floatwrite (trace,nt,out);
	    }
	}
    }

    exit(0);
}
Пример #22
0
int main(int argc, char *argv[])
{
    int nk, nh, iw, nw, i4, n4, ik;
    float k0, dk, h0, dh, w0, dw, w, k, eps; 
    bool inv, verb, adj, dwt;

    char *type;
    sf_complex *pp, *qq;
    sf_file in, out;

    sf_init(argc,argv);

    in = sf_input("in");
    out = sf_output("out");

    if (SF_COMPLEX != sf_gettype(in)) sf_error("Need complex input");

    if (!sf_histint(in,"n1",&nh)) sf_error("No n1= in input");
    if (!sf_histint(in,"n2",&nk)) sf_error("No n2= in input");
    if (!sf_histint(in,"n3",&nw)) sf_error("No n3= in input");

    if (!sf_histfloat(in,"d1",&dh)) sf_error("No d1= in input");
    if (!sf_histfloat(in,"d2",&dk)) sf_error("No d2= in input");
    if (!sf_histfloat(in,"d3",&dw)) sf_error("No d3= in input");

    if (!sf_histfloat(in,"o1",&h0)) sf_error("No o1= in input");
    if (!sf_histfloat(in,"o2",&k0)) sf_error("No o2= in input");
    if (!sf_histfloat(in,"o3",&w0)) sf_error("No o3= in input");

    n4 = sf_leftsize(in,3);

    if (!sf_getbool("inv",&inv)) inv=false;
    /* if y, do inverse transform */

    if (!sf_getbool("adj",&adj)) adj=false;
    /* if y, do adjoint transform */

    if (!sf_getbool("dwt",&dwt)) dwt=false;
    /* if y, do wavelet transform */

    if (!sf_getbool("verb",&verb)) verb=true;
    /* verbosity flag */

    if (!sf_getfloat("eps",&eps)) eps=0.01;
    /* regularization */

    pp = sf_complexalloc(nh);   /* data space */
    qq = sf_complexalloc(nh);   /* model space */

    if (NULL == (type=sf_getstring("type"))) type="biorthogonal";
    /* [haar,linear,biorthogonal] wavelet type, the default is biorthogonal  */

    fkoclet_init(nh,nk,dh,dk,dw,h0,k0,inv,false,dwt,eps*eps,type[0]);

    /* loop over n4 */
    for (i4=0; i4 < n4; i4++) {
	for (iw=0; iw < nw; iw++) { /* loop over frequency */
	    if (verb) sf_warning("frequency %d of %d;",iw+1,nw);
	    w = w0 + iw*dw;
	    for (ik=0; ik < nk; ik++) { /* loop over wavenumber */
		k = k0 + ik*dk;
		if (adj) {
		    sf_complexread(qq,nh,in);
		} else {
		    sf_complexread(pp,nh,in);
		} 

		if (adj) {
		    fkoclet_lop(false,false,nh,nh,qq,pp,w,k);
		    sf_complexwrite(pp,nh,out);
		} else {
		    fkoclet_lop(true,false,nh,nh,qq,pp,w,k);
		    sf_complexwrite(qq,nh,out);
		} 
	    }
	}
    }
    sf_warning(".");
    exit(0);
}
Пример #23
0
int main(int argc, char * argv[])
{

    sf_file inA, outC, inB;
    int an1, an2, bn1, bn2;
    int im, in, ik, m, n, k, nth;
    
    sf_complex **a, **b, **c;
    sf_axis aax1, aax2, bax1, bax2, cax1, cax2;
    
    /* init RSF */
    sf_init (argc, argv);
    inA = sf_input("in");
    inB = sf_input("B");
    outC= sf_output("out");

    if(SF_COMPLEX != sf_gettype(inA)) sf_error("Need complex input!");
    if(SF_COMPLEX != sf_gettype(inB)) sf_error("Need complex input!");
    
    if(!sf_histint(inA, "n1", &an1)) sf_error("No n1 in input");
    if(!sf_histint(inB, "n1", &bn1)) sf_error("No n1 in input");
    if(!sf_histint(inA, "n2", &an2)) an2 = 1;
    if(!sf_histint(inB, "n2", &bn2)) bn2 = 1;

    if(sf_leftsize(inA,2)>1) sf_error("Input should be a matrix!");
    if(sf_leftsize(inB,2)>1) sf_error("Input should be a matrix!");
    
    if(an2 != bn1) sf_error("Input do not match!");

    aax1 = sf_iaxa(inA, 1);
    aax2 = sf_iaxa(inA, 2);
    bax1 = sf_iaxa(inB, 1);
    bax2 = sf_iaxa(inB, 2);
    
    cax1 = aax1;
    cax2 = bax2;
    
    a = sf_complexalloc2(an1, an2);
    b = sf_complexalloc2(bn1, bn2);
    
    sf_complexread(a[0], an1*an2, inA);
    sf_complexread(b[0], bn1*bn2, inB);

    m = an1;
    n = an2;
    k = bn2;
    
#ifdef _OPENMP
#pragma omp parallel
    {
      nth = omp_get_num_threads();
      /* omp_set_num_threads(nth); */
    }
    sf_warning(">>>> Using %d threads <<<<<", nth);
#endif

    c = sf_complexalloc2(m,k);
#ifdef _OPENMP
#pragma omp parallel for private(im,ik) shared(c,a,b,an1,an2,bn2)
#endif
    for(im=0; im< an1; im++) {
	for (ik=0; ik<bn2; ik++ ) {
	    c[ik][im]=sf_cmplx(0.0,0.0);
	    for (in=0; in<an2; in++) {
#ifdef SF_HAS_COMPLEX_H
		c[ik][im]+=a[in][im]*b[ik][in];
#else
		c[ik][im]+=sf_cmul(a[in][im],b[ik][in]);
#endif
	    }
	}
    }
    sf_oaxa(outC, cax1, 1);
    sf_oaxa(outC, cax2, 2);
    
    sf_complexwrite(c[0], m*k, outC);

    exit(0);
    
}
Пример #24
0
int main(int argc, char* argv[])
{
    bool verb,complx,sub,os;
    int it,iz,im,ik,ix,i,j;     /* index variables */
    int nt,nz,nx, m2, nk, nzx, nz2, nx2, nzx2, n2, pad1,nth;
    sf_complex c,old;

    /* I/O arrays*/
    sf_complex *ww,*curr,*prev,*cwave,*cwavem,**wave,**lt, **rt;
    float *rcurr,*rr;

    sf_file Fw,Fr,Fo;    /* I/O files */
    sf_axis at,az,ax;    /* cube axes */
    sf_file left, right;


    sf_init(argc,argv);
    if(!sf_getbool("verb",&verb)) verb=false; /* verbosity */
    if(!sf_getbool("cmplx",&complx)) complx=true; /* outputs complex wavefield */
    if(!sf_getbool("os",&os)) os=true; /* one-step flag */
    if (os) {
        sf_warning("One-step wave extrapolation");
        if(!sf_getbool("sub",&sub)) sub=false; /* subtraction flag */
    } else {
        sf_warning("Two-step wave extrapolation");
        if(!sf_getbool("sub",&sub)) sub=true; /* subtraction flag */
    }

    /* setup I/O files */
    Fw = sf_input ("in" );
    Fo = sf_output("out");
    Fr = sf_input ("ref");

    if (SF_COMPLEX != sf_gettype(Fw)) sf_error("Need complex input");
    if (SF_FLOAT != sf_gettype(Fr)) sf_error("Need float ref");

    if(complx)
        sf_settype(Fo,SF_COMPLEX);
    else
        sf_settype(Fo,SF_FLOAT);

    /* Read/Write axes */
    at = sf_iaxa(Fw,1);
    nt = sf_n(at);
    az = sf_iaxa(Fr,1);
    nz = sf_n(az);
    ax = sf_iaxa(Fr,2);
    nx = sf_n(ax);

    sf_oaxa(Fo,az,1);
    sf_oaxa(Fo,ax,2);
    sf_oaxa(Fo,at,3);

    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */

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

    nk = cfft2_init(pad1,nz,nx,&nz2,&nx2);

    nzx = nz*nx;
    nzx2 = nz2*nx2;

    /* propagator matrices */
    left = sf_input("left");
    right = sf_input("right");

    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");

    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);

    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);

    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);

    sf_fileclose(left);
    sf_fileclose(right);

    /* read wavelet & reflectivity */
    ww=sf_complexalloc(nt);
    sf_complexread(ww,nt ,Fw);

    rr=sf_floatalloc(nzx);
    sf_floatread(rr,nzx,Fr);

    curr   = sf_complexalloc(nzx2);
    if (!os) prev = sf_complexalloc(nzx2);
    else prev = NULL;
    if(!complx) rcurr  = sf_floatalloc(nzx2);
    else rcurr=NULL;

    cwave  = sf_complexalloc(nk);
    cwavem = sf_complexalloc(nk);
    wave   = sf_complexalloc2(nzx2,m2);

    for (iz=0; iz < nzx2; iz++) {
        curr[iz] = sf_cmplx(0.,0.);
        if (!os) prev[iz] = sf_cmplx(0.,0.);
        if(!complx) rcurr[iz]= 0.;
    }

    /* MAIN LOOP */
    for (it=0; it<nt; it++) {
        if(verb) sf_warning("it=%d;",it);

        /* matrix multiplication */
        cfft2(curr,cwave);

        for (im = 0; im < m2; im++) {
            for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
                cwavem[ik] = cwave[ik]*rt[ik][im];
#else
                cwavem[ik] = sf_cmul(cwave[ik],rt[ik][im]); //complex multiplies complex
#endif
            }
            icfft2(wave[im],cwavem);
        }

        for (ix = 0; ix < nx; ix++) {
            for (iz=0; iz < nz; iz++) {
                i = iz+ix*nz;  /* original grid */
                j = iz+ix*nz2; /* padded grid */
#ifdef SF_HAS_COMPLEX_H
                c = ww[it] * rr[i]; // source term
#else
                c = sf_crmul(ww[it], rr[i]); // source term
#endif
                if (sub) c += curr[j];
                if (!os) {
                    old = curr[j];
#ifdef SF_HAS_COMPLEX_H
                    c += sub? (old-prev[j]) : -prev[j];
#else
                    c = sf_cadd(c,sub? sf_csub(old,prev[j]) : sf_cneg(prev[j]));
#endif
                    prev[j] = old;
                }
                for (im = 0; im < m2; im++) {
#ifdef SF_HAS_COMPLEX_H
                    c += lt[im][i]*wave[im][j];
#else
                    c += sf_cmul(lt[im][i], wave[im][j]);
#endif
                }

                curr[j] = c;
                if (!complx) rcurr[j] = crealf(c);

            }

            /* write wavefield to output */
            if (complx)
                sf_complexwrite(curr+ix*nz2,nz,Fo);
            else
                sf_floatwrite(rcurr+ix*nz2,nz,Fo);
        }
    }
    if(verb) sf_warning(".");
    cfft2_finalize();
    exit (0);
}
Пример #25
0
int main(int argc, char* argv[]) 
{
    clock_t tstart,tend;
    double duration;

    /*flag*/
    bool verb, adj; /* migration(adjoint) flag */
    bool wantwf;
    bool wantrecord; /* actually means "need record" */
    
    /*I/O*/
    sf_file Fvel;
    sf_file left, right, leftb, rightb;
    sf_file Fsrc, Frcd/*source and record*/;
    sf_file Ftmpwf, Ftmpbwf;
    sf_file Fimg;

    sf_axis at, ax, az;

    /*grid index variables*/
    int nx, nz, nt, wfnt;
    int nzx, nx2, nz2, n2, m2, pad1, nk;
    int ix, it;
    int nxb, nzb;
    float dt, dx, dz, wfdt;
    float ox, oz;

    /*source/geophone location*/
    float slx, slz;
    int   spx, spz;
    float gdep;
    int   gpz,gpx,gpl; /*geophone depth/x-crd/length*/

    /*Model*/
    sf_complex **lt, **rt;
    sf_complex **ltb, **rtb;

    /*Data*/
    sf_complex ***wavefld, ***wavefld2;
    sf_complex **record, **img;
    float **sill;
    int snpint;

    /*source*/
    sf_complex *ww;
    float *rr;
    int rectz,rectx,repeat; /*smoothing parameters*/
    float trunc;

    /*abc boundary*/
    int top,bot,lft,rht;

    /*memoray*/
    int tmpint;

    tstart = clock();
    sf_init(argc, argv);
    if (!sf_getbool("verb", &verb)) verb=false; /*verbosity*/
    if (!sf_getbool("adj", &adj)) adj=true; /*migration*/
    if (!sf_getbool("wantwf", &wantwf)) wantwf=false; /*output forward and backward wavefield*/
    if (!sf_getbool("wantrecord", &wantrecord)) wantrecord=true; /*if n, using record data generated by this program */

    /*Set I/O file*/

    if (adj) { /* migration */
      if (wantrecord) {
	Frcd = sf_input("in"); /*record from elsewhere*/
	Fsrc  = sf_input("src");   /*source wavelet*/      
      } else {
	Frcd = sf_output("rec"); /*record produced by forward modeling*/
	Fsrc = sf_input("in");   /*source wavelet*/
      }
      Fimg  = sf_output("out");
    } else { /* modeling */
      Fimg = sf_input("in");
      Frcd = sf_output("out");
      Fsrc  = sf_input("src");   /*source wavelet*/      
    }

    Fvel  = sf_input("vel");  /*velocity - just for model dimension*/
    if (wantwf) {
	Ftmpwf  = sf_output("tmpwf");/*wavefield snap*/
	Ftmpbwf = sf_output("tmpbwf");
    }

    /*--- Axes parameters ---*/
    at = sf_iaxa(Fsrc, 1); nt = sf_n(at);  dt = sf_d(at);      
    az = sf_iaxa(Fvel, 1); nzb = sf_n(az); dz = sf_d(az); oz = sf_o(az);
    ax = sf_iaxa(Fvel, 2); nxb = sf_n(ax); dx = sf_d(ax); ox = sf_o(ax);
    nzx = nzb*nxb;

    /*--- parameters of source ---*/
    if (!sf_getfloat("srctrunc", &trunc)) trunc=0.4;
    if (!sf_getint("rectz", &rectz)) rectz=1;
    if (!sf_getint("rectx", &rectx)) rectx=1;
    if (!sf_getint("repeat", &repeat)) repeat=0;
    ww=sf_complexalloc(nt);
    rr=sf_floatalloc(nzx);

    /* propagator matrices */
    left  = sf_input("left");
    right = sf_input("right");
    leftb  = sf_input("leftb");
    rightb = sf_input("rightb");

    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */
    nz2 = kiss_fft_next_fast_size(nzb*pad1);
    nx2 = kiss_fft_next_fast_size(nxb);
    nk = nz2*nx2; /*wavenumber*/

    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");
    
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);
  
    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);
    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);

    ltb = sf_complexalloc2(nzx,m2);
    rtb = sf_complexalloc2(m2,nk);
    sf_complexread(ltb[0],nzx*m2,leftb);
    sf_complexread(rtb[0],m2*nk,rightb);

    sf_fileclose(left);
    sf_fileclose(right);
    sf_fileclose(leftb);
    sf_fileclose(rightb);

    /* abc parameters */
    if (!sf_getint("top", &top)) top=40;
    if (!sf_getint("bot", &bot)) bot=40;
    if (!sf_getint("lft", &lft)) lft=40;
    if (!sf_getint("rht", &rht)) rht=40;
    /* Width of abc layer */

    nz = nzb - top - bot;
    nx = nxb - lft - rht;

    /*Geometry parameters*/
    geopar geop;
    geop = creategeo();
 
    /*source loaction parameters*/

    if (!sf_getfloat("slx", &slx)) slx=-1.0; 
    /*source location x */
    if (!sf_getint("spx", &spx)) spx=-1;
    /*source location x (index)*/
    if((slx<0 && spx <0) || (slx>=0 && spx >=0 ))  sf_error("Need src location");
    if (slx >= 0 )    spx = (int)((slx-ox)/dx+0.5);
    
    if (!sf_getfloat("slz", &slz)) slz=-1.0;
    /* source location z */
    if (!sf_getint("spz", &spz)) spz=-1;
    /*source location z (index)*/
    if((slz<0 && spz <0) || (slz>=0 && spz >=0 ))  sf_error("Need src location");
    if (slz >= 0 )    spz = (int)((slz-ox)/dz+0.5);
    
    if (!sf_getfloat("gdep", &gdep)) gdep=-1.0;
    /* recorder depth on grid*/
    if (!sf_getint("gpz", &gpz)) gpz=0;
    /* recorder depth on index*/
    if (!sf_getint("gpx", &gpx)) sf_error("Need receiver starting location");
    /* recorder starting location on index*/   
    if (!sf_getint("gpl", &gpl)) sf_error("Need receiver length");
    /* recorder length on index*/
    if ( gdep>=oz) { gpz = (int)((gdep-oz)/dz+0.5);}
    if (gpz < 0.0) sf_error("gdep need to be >=oz");
    /*source and receiver location*/

    if (!sf_getint("snapinter", &snpint)) snpint=10;
    /* snap interval */

    /*load source wavelet and reflectivity map*/
    ww=sf_complexalloc(nt);  
    sf_complexread(ww,nt,Fsrc);
    sf_fileclose(Fsrc);
    reflgen(nzb, nxb, spz+top, spx+lft, rectz, rectx, repeat, rr);
    /*check record data*/
    if (adj && wantrecord){
	sf_histint(Frcd,"n1", &tmpint);
	if (tmpint != nt ) sf_error("Error parameter n1 in record!");
	sf_histint(Frcd,"n2", &tmpint);
	if (tmpint != gpl ) sf_error("Error parameter n2 in record!");
    }
    
    geop->nx  = nx;
    geop->nz  = nz;
    geop->nxb = nxb;
    geop->nzb = nzb;
    geop->dx  = dx;
    geop->dz  = dz;
    geop->ox  = ox;
    geop->oz  = oz;
    geop->snpint = snpint;
    geop->spx = spx;
    geop->spz = spz;
    geop->gpz = gpz;
    geop->gpx = gpx;
    geop->gpl = gpl;
    geop->top = top;
    geop->bot = bot;
    geop->lft = lft;
    geop->rht = rht;
    geop->nt = nt;
    geop->dt = dt;
    geop->trunc = trunc;

    /* wavefield and record  */
    wfnt = (int)(nt-1)/snpint+1;
    wfdt = dt*snpint;
    record = sf_complexalloc2(nt, gpl);
    wavefld = sf_complexalloc3(nz, nx, wfnt);
    sill = sf_floatalloc2(nz, nx);
    if (wantwf)
	wavefld2= sf_complexalloc3(nz, nx, wfnt);
    else
	wavefld2=NULL;

    /*image*/
    img = sf_complexalloc2(nz, nx);

    if (verb) {
	sf_warning("============================");
	sf_warning("nx=%d nz=%d nt=%d", geop->nx, geop->nz, geop->nt);
	sf_warning("nxb=%d nzb=%d ", geop->nxb, geop->nzb);
	sf_warning("dx=%f dz=%f dt=%f", geop->dx, geop->dz, geop->dt);
	sf_warning("top=%d bot=%d lft=%d rht=%d", geop->top, geop->bot, geop->lft, geop->rht);
	sf_warning("rectz=%d rectx=%d repeat=%d srctrunc=%f",rectz,rectx,repeat,geop->trunc);
	sf_warning("spx=%d spz=%d gpz=%d gpx=%d gpl=%d snpint=%d", spx, spz, gpz, gpx, gpl, snpint);
	sf_warning("wfdt=%f wfnt=%d ", wfdt, wfnt);
	sf_warning("============================");
    }

    /* write record */
    sf_setn(ax, gpl);
    sf_setn(az, nz);

    if (adj) { /* migration */
      if(!wantrecord) {
	sf_oaxa(Frcd, at, 1);
	sf_oaxa(Frcd, ax, 2);
	sf_settype(Frcd,SF_COMPLEX);	
      }
      sf_setn(ax, nx);
      /*write image*/
      sf_oaxa(Fimg, az, 1);
      sf_oaxa(Fimg, ax, 2);
      sf_settype(Fimg,SF_COMPLEX);
    } else { /* modeling */
      sf_oaxa(Frcd, at, 1);
      sf_oaxa(Frcd, ax, 2);
      sf_settype(Frcd,SF_COMPLEX);
    }

    if (wantwf) {
      sf_setn(ax, nx);
      /*write temp wavefield */
      sf_setn(at, wfnt);
      sf_setd(at, wfdt);
      
      sf_oaxa(Ftmpwf, az, 1);
      sf_oaxa(Ftmpwf, ax, 2);
      sf_oaxa(Ftmpwf, at, 3);
      sf_settype(Ftmpwf,SF_COMPLEX);
      
      /*write temp wavefield */
      sf_oaxa(Ftmpbwf, az, 1);
      sf_oaxa(Ftmpbwf, ax, 2);
      sf_oaxa(Ftmpbwf, at, 3);
      sf_settype(Ftmpbwf,SF_COMPLEX);
    }
    
    if (!adj) sf_complexread(img[0],nx*nz,Fimg);

    lrosfor2(wavefld, sill, record, verb, lt, rt, m2, geop, ww, rr, pad1);

    if(adj && wantrecord) sf_complexread(record[0], gpl*nt, Frcd);

    lrosback2(img, wavefld, sill, record, adj, verb, wantwf, ltb, rtb, m2, geop, pad1, wavefld2);

    if (!wantrecord || !adj) {
      for (ix=0; ix<gpl; ix++) {
	sf_complexwrite(record[ix], nt, Frcd);
      }
    }
    if (adj) {
      for (ix=0; ix<nx; ix++) 
	sf_complexwrite(img[ix], nz, Fimg);
    }

    if (wantwf) {
	for (it=0; it<wfnt; it++)
	    for ( ix=0; ix<nx; ix++) {
		sf_complexwrite(wavefld[it][ix], nz, Ftmpwf);
		sf_complexwrite(wavefld2[it][ix],nz, Ftmpbwf);
	    }
    }

    tend = clock();
    duration=(double)(tend-tstart)/CLOCKS_PER_SEC;
    sf_warning(">> The CPU time of single shot migration is: %f seconds << ", duration);
    exit(0);
}
Пример #26
0
int main(int argc, char* argv[])
{
    sf_file Fw_s=NULL, Fw_r=NULL;
    sf_file Fi=NULL, Fm=NULL, Fr=NULL;
    sf_axis ag,at,aw,ar;
    int ig,it,iw,ir;
    int ng,nt,nw,nr;

    int method;
    bool  verb;
    bool   adj;

    sf_complex **dat_s=NULL, *wfl_s=NULL;
    sf_complex **dat_r=NULL, *wfl_r=NULL;
    float      **img=NULL;
    float      **aa=NULL,**bb=NULL,**mm=NULL;

    sf_complex **ab=NULL;
    float      **a0=NULL,**b0=NULL;

    float w,ws,wr,w0,dw;
    char *met="";

    sf_init(argc,argv);

    if(! sf_getbool("verb", &verb))     verb=false;
    if(! sf_getint("method",&method)) method=0;    /* extrapolation method */
    if(! sf_getbool("adj",  &adj))       adj=false;/* y=modeling; n=migration */
    Fm = sf_input("abm");
    Fr = sf_input("abr");

    at=sf_iaxa(Fm,2); sf_setlabel(at,"t"); /* 'extrapolation axis' */
    ar=sf_iaxa(Fr,1); sf_setlabel(ar,"r"); /* a,b reference */
    if(method==0) sf_setn(ar,1); /* pure F-D */
    nr=sf_n(ar); 

    Fw_s = sf_input ( "in");
    if (SF_COMPLEX !=sf_gettype(Fw_s)) sf_error("Need complex source");

    /* 'position axis' (could be angle) */
    ag = sf_iaxa(Fw_s,1); ng=sf_n(ag); sf_setlabel(ag,"g"); 

    /* 'extrapolation axis' (could be time) */
    at = sf_iaxa(Fw_s,2); nt=sf_n(at); sf_setlabel(at,"t");
    aw = sf_iaxa(Fw_s,3); sf_setlabel(aw,"w"); /* frequency */

    if(adj) { /* modeling */
	Fw_r = sf_output("out"); 
	sf_settype(Fw_r,SF_COMPLEX);

	Fi   = sf_input ("img");
	if (SF_FLOAT !=sf_gettype(Fi)) sf_error("Need float image");

	sf_oaxa(Fw_r,ag,1);
	sf_oaxa(Fw_r,at,2);
	sf_oaxa(Fw_r,aw,3);
    } else {  /* migration */
	Fw_r = sf_input ("rwf");
	if (SF_COMPLEX !=sf_gettype(Fw_r)) sf_error("Need complex data");

	Fi   = sf_output("out"); 
	sf_settype(Fi,SF_FLOAT);
		
	sf_oaxa(Fi,ag,1);
	sf_oaxa(Fi,at,2);
	sf_putint(Fi,"n3",1);
    }

    img   = sf_floatalloc2  (ng,nt);
    dat_s = sf_complexalloc2(ng,nt);
    dat_r = sf_complexalloc2(ng,nt);
    wfl_s = sf_complexalloc (ng);
    wfl_r = sf_complexalloc (ng);

    if(verb) {
	sf_raxa(ag);
	sf_raxa(at);
	sf_raxa(aw);
	sf_raxa(ar);
    }

    /* read ABM */
    aa = sf_floatalloc2  (ng,nt);
    bb = sf_floatalloc2  (ng,nt);
    mm = sf_floatalloc2  (ng,nt);

    sf_floatread(aa[0],ng*nt,Fm); /* a coef */
    sf_floatread(bb[0],ng*nt,Fm); /* b coef */
    sf_floatread(mm[0],ng*nt,Fm); /* mask */

    /* read ABr */
    ab = sf_complexalloc2(nr,nt);
    a0 = sf_floatalloc2  (nr,nt);
    b0 = sf_floatalloc2  (nr,nt);

    sf_complexread(ab[0],nr*nt,Fr);
    for(it=0;it<nt;it++) {
	for(ir=0;ir<nr;ir++) {
	    a0[it][ir] = crealf(ab[it][ir]);
	    b0[it][ir] = cimagf(ab[it][ir]);
	}
    }

/*------------------------------------------------------------*/
    switch (method) {
	case 3: met="PSC"; break;
	case 2: met="FFD"; break;
	case 1: met="SSF"; break;
	case 0: met="XFD"; break;
    }

    /* from hertz to radian */
    nw = sf_n(aw);
    dw = sf_d(aw) * 2.*SF_PI; 
    w0 = sf_o(aw) * 2.*SF_PI;

    rweone_init(ag,at,aw,ar,method,verb);
    switch(method) {
	case 3: rweone_psc_coef(aa,bb,a0,b0); break;
	case 2: rweone_ffd_coef(aa,bb,a0,b0); break;
	case 1: ;/* SSF */                    break;
	case 0: rweone_xfd_coef(aa,bb);       break;
    }

    if(adj) { /* modeling */
	
    } else {  /* migration */
	for(it=0;it<nt;it++) {
	    for(ig=0;ig<ng;ig++) {
		img[it][ig] = 0.;
	    }
	}
    }

/*------------------------------------------------------------*/
    if( adj)  sf_floatread  (img[0],ng*nt,Fi);

    for(iw=0;iw<nw;iw++) {
	w=w0+iw*dw;
	sf_warning("%s %d %d",met,iw,nw);

	if(adj) {
	    sf_complexread(dat_s[0],ng*nt,Fw_s);

	    ws = -w; /*      causal */
	    for(ig=0;ig<ng;ig++) {
		wfl_s[ig] = sf_cmplx(0.,0.);
	    }
	    for(it=0;it<nt;it++) {
		for(ig=0;ig<ng;ig++) {
#ifdef SF_HAS_COMPLEX_H
		    wfl_s[ig] += dat_s[it][ig];
		    dat_r[it][ig] = wfl_s[ig]*img[it][ig];
#else
		    wfl_s[ig] = sf_cadd(wfl_s[ig],dat_s[it][ig]);
		    dat_r[it][ig] = sf_crmul(wfl_s[ig],img[it][ig]);
#endif
		}
		
		if(method!=0) rweone_fk(ws,wfl_s,aa[it],a0[it],b0[it],mm[it],it);
		else          rweone_fx(ws,wfl_s,aa[it],it);
		rweone_tap(wfl_s);
	    }

	    for(it=0;it<nt;it++) {
		for(ig=0;ig<ng;ig++) {
		    dat_s[it][ig] = dat_r[it][ig];
		}
	    }

	    wr = -w; /*      causal */
	    for(ig=0;ig<ng;ig++) {
		wfl_r[ig] = sf_cmplx(0.,0.);
	    }
	    for(it=nt-1;it>=0;it--) {
		for(ig=0;ig<ng;ig++) {
#ifdef SF_HAS_COMPLEX_H
		    wfl_r[ig] += dat_s[it][ig];
#else
		    wfl_r[ig] = sf_cadd(wfl_r[ig],dat_s[it][ig]);
#endif
		    dat_r[it][ig] = wfl_r[ig];
		}
		
		if(method!=0) rweone_fk(wr,wfl_r,aa[it],a0[it],b0[it],mm[it],it);
		else          rweone_fx(wr,wfl_r,aa[it],it);
		rweone_tap(wfl_r);
	    }

	    sf_complexwrite(dat_r[0],ng*nt,Fw_r);

	} else {
	    ws = -w; /*      causal */
	    wr = +w; /* anti-causal */

	    sf_complexread(dat_s[0],ng*nt,Fw_s);
	    sf_complexread(dat_r[0],ng*nt,Fw_r);

	    for(ig=0;ig<ng;ig++) {
		wfl_s[ig] = sf_cmplx(0,0);
		wfl_r[ig] = sf_cmplx(0,0);
	    }

	    for(it=0;it<=nt-2;it++) {
		for(ig=0;ig<ng;ig++) {
#ifdef SF_HAS_COMPLEX_H
		    wfl_s[ig] += dat_s[it][ig];
		    wfl_r[ig] += dat_r[it][ig];
#else
		    wfl_s[ig] = sf_cadd(wfl_s[ig],dat_s[it][ig]);
		    wfl_r[ig] = sf_cadd(wfl_r[ig],dat_r[it][ig]);
#endif
		}

		rweone_spi(wfl_s,wfl_r,img[it]);
		
		if(method!=0) {
		    rweone_fk(ws,wfl_s,aa[it],a0[it],b0[it],mm[it],it);
		    rweone_fk(wr,wfl_r,aa[it],a0[it],b0[it],mm[it],it);
		} else {
		    rweone_fx(ws,wfl_s,aa[it],it);
		    rweone_fx(wr,wfl_r,aa[it],it);
		}
	    }
	    it=nt-1; rweone_spi(wfl_s,wfl_r,img[it]);
	}
    }

    if(!adj)  sf_floatwrite  (img[0],ng*nt,Fi);
/*------------------------------------------------------------*/

    exit(0);
}
Пример #27
0
int main(int argc, char* argv[])
{
    bool verb,correct;
    int nt,nz,nx,m2,nk,nzx,nz2,nx2,n2,pad1;
    int snap, wfnt;
    float dt, wfdt;
    char *mode;

    sf_complex **ini, **cc, **dd;
    
    sf_file Fi,Fo,Fs,Fa,Fb;    /* I/O files */
    sf_axis az,ax,at;    /* cube axes */

    sf_complex **lt, **rt,***wvfld,*alpha,*beta;
    sf_file left, right;

    sf_init(argc,argv);
    if(!sf_getbool("verb",&verb)) verb=true; /* verbosity */
    if(!sf_getint("nt",&nt)) sf_error("Need nt!"); 
    if(!sf_getfloat("dt",&dt)) sf_error("Need dt!");
    if(!sf_getint("snap",&snap)) snap=0;     /* interval for snapshots */
    if(!sf_getbool("correct",&correct)) correct=false; /*jingwei's correction*/
    mode=sf_getstring("mode"); /* default mode is pspi */
    
    if (mode[0]=='p') {sf_warning(">>>>> Using PSPI+PSPI! <<<<< \n");}
    else if (mode[0]=='n') {sf_warning(">>>>> Using NSPS+NSPS! <<<<< \n");}
    else if (mode[0]=='m') {sf_warning(">>>>> Using NSPS+PSPI! <<<<< \n");}
    else if (mode[0]=='x') {sf_warning(">>>>> Using PSPI+NSPS! <<<<< \n");}
    else sf_error("Specify mode!");

    /* setup I/O files */
    Fi = sf_input ("in" );
    Fo = sf_output("out");
    sf_settype(Fo,SF_COMPLEX);

    /* Read/Write axes */
    az = sf_iaxa(Fi,1); nz = sf_n(az); 
    ax = sf_iaxa(Fi,2); nx = sf_n(ax); 
    at = sf_iaxa(Fi,3);

    sf_oaxa(Fo,az,1); 
    sf_oaxa(Fo,ax,2); 

    if (snap > 0) {
      Fs = sf_output("snaps");	/* (optional) snapshot file */
      wfnt = (int)(nt-1)/snap + 1;
      wfdt = dt*snap;
      sf_oaxa(Fs,az,1); 
      sf_oaxa(Fs,ax,2); 
      sf_setn(at,wfnt);
      sf_setd(at,wfdt);
      sf_oaxa(Fs,at,3);
      sf_settype(Fs,SF_COMPLEX);
    } else Fs=NULL;

    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */

    nz2 = kiss_fft_next_fast_size(nz*pad1);
    nx2 = kiss_fft_next_fast_size(nx);
    nk = nz2*nx2; /*wavenumber*/
    nzx = nz*nx;

    /* propagator matrices */
    left = sf_input("left");
    right = sf_input("right");

    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");
    
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);
  
    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);

    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);

    sf_fileclose(left);
    sf_fileclose(right);

    ini=sf_complexalloc2(nz,nx);
    cc=sf_complexalloc2(nz,nx);
    dd=sf_complexalloc2(nz,nx);

    sf_complexread(ini[0],nzx,Fi);
    sf_fileclose(Fi);

    if (snap>0) wvfld = sf_complexalloc3(nz,nx,wfnt);
    else wvfld = NULL;

    if (correct) {
	Fa = sf_input("alpha");
	Fb = sf_input("beta");
	
	if (!sf_histint(Fa,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in alpha",nzx);
	if (!sf_histint(Fb,"n1",&n2) || n2 != nk) sf_error("Need n1=%d in beta",nk);
	
	alpha = sf_complexalloc(nzx);
	beta = sf_complexalloc(nk);
	
	sf_complexread(alpha,nzx,Fa);
	sf_complexread(beta,nk,Fb);
	
	sf_fileclose(Fa);
	sf_fileclose(Fb);
    } else {
	Fa = NULL; Fb = NULL;
	alpha = NULL; beta = NULL;
    }

    /* wave propagation*/

    propnewc(ini, lt, rt, nz, nx, nt, m2, nk, mode, 1, snap, cc, wvfld, verb,correct,alpha,beta);

    /* output result */
    sf_complexwrite(cc[0], nzx, Fo);
    if (snap>0)
      sf_complexwrite(wvfld[0][0], nzx*wfnt, Fs);

    exit (0);
}
Пример #28
0
int main(int argc, char* argv[])
{
    bool verb,complx;        
    int it,iz,im,ik,ix,i,j;     /* index variables */
    int nt,nz,nx, m2, nk, nzx, nz2, nx2, nzx2, n2, pad1;
    sf_complex c;

    float  *rr;      /* I/O arrays*/
    sf_complex *ww, *cwave, *cwavem;

    sf_complex **wave,**wave2, *curr, *currm;
    float *rcurr=NULL;
    
    sf_file Fw,Fr,Fo;    /* I/O files */
    sf_axis at,az,ax;    /* cube axes */

    sf_complex **lt, **rt;
    sf_file left, right;


    sf_init(argc,argv);
    if(!sf_getbool("verb",&verb)) verb=false; /* verbosity */
    if(!sf_getbool("cmplx",&complx)) complx=true; /* outputs complex wavefield */

    /* setup I/O files */
    Fw = sf_input ("in" );
    Fo = sf_output("out");
    Fr = sf_input ("ref");

    if (SF_COMPLEX != sf_gettype(Fw)) sf_error("Need complex input");
    if (SF_FLOAT != sf_gettype(Fr)) sf_error("Need float ref");

    if(complx)
	sf_settype(Fo,SF_COMPLEX);
    else
	sf_settype(Fo,SF_FLOAT);

    /* Read/Write axes */
    at = sf_iaxa(Fw,1); nt = sf_n(at); 
    az = sf_iaxa(Fr,1); nz = sf_n(az); 
    ax = sf_iaxa(Fr,2); nx = sf_n(ax); 

    sf_oaxa(Fo,az,1); 
    sf_oaxa(Fo,ax,2); 
    sf_oaxa(Fo,at,3);
    
    if (!sf_getint("pad1",&pad1)) pad1=1; /* padding factor on the first axis */

    nk = cfft2_init(pad1,nz,nx,&nz2,&nx2);

    nzx = nz*nx;
    nzx2 = nz2*nx2;

    /* propagator matrices */
    left = sf_input("left");
    right = sf_input("right");

    if (!sf_histint(left,"n1",&n2) || n2 != nzx) sf_error("Need n1=%d in left",nzx);
    if (!sf_histint(left,"n2",&m2))  sf_error("Need n2= in left");
    
    if (!sf_histint(right,"n1",&n2) || n2 != m2) sf_error("Need n1=%d in right",m2);
    if (!sf_histint(right,"n2",&n2) || n2 != nk) sf_error("Need n2=%d in right",nk);
  
    lt = sf_complexalloc2(nzx,m2);
    rt = sf_complexalloc2(m2,nk);

    sf_complexread(lt[0],nzx*m2,left);
    sf_complexread(rt[0],m2*nk,right);

    sf_fileclose(left);
    sf_fileclose(right);

    /* read wavelet & reflectivity */
    ww=sf_complexalloc(nt);  
    sf_complexread(ww,nt ,Fw);

    rr=sf_floatalloc(nzx); 
    sf_floatread(rr,nzx,Fr);

    curr   = sf_complexalloc(nzx2);
    currm  = sf_complexalloc(nzx2);
    
    if(!complx) rcurr  = sf_floatalloc(nzx2);

    cwave  = sf_complexalloc(nk);
    cwavem  = sf_complexalloc(nk);
    wave   = sf_complexalloc2(nk,m2);
    wave2  = sf_complexalloc2(nzx2,m2);

    for (iz=0; iz < nzx2; iz++) {
	curr[iz] = sf_cmplx(0.,0.);
	if(!complx) rcurr[iz]= 0.;
    }

    /* MAIN LOOP */
    for (it=0; it<nt; it++) {
	if(verb) sf_warning("it=%d;",it);

	/* matrix multiplication */
	for (im = 0; im < m2; im++) {
	    for (ix = 0; ix < nx; ix++) {
		for (iz=0; iz < nz; iz++) {
		    i = iz+ix*nz;  /* original grid */
		    j = iz+ix*nz2; /* padded grid */
#ifdef SF_HAS_COMPLEX_H
		    currm[j] = lt[im][i]*curr[j];
#else
		    currm[j] = sf_cmul(lt[im][i], curr[j]);
#endif
		}
	    }
	    cfft2(currm,wave[im]);
	}

/* approach no.2 */
	for (ik = 0; ik < nk; ik++) {
	    c = sf_cmplx(0.,0.);
	    for (im = 0; im < m2; im++) {
#ifdef SF_HAS_COMPLEX_H
		c += wave[im][ik]*rt[ik][im];
#else
		c = sf_cadd(c,sf_cmul(wave[im][ik],rt[ik][im])); /* complex multiplies complex */
#endif
	    }
	    cwave[ik] = c;
	}

	for (im = 0; im < m2; im++) {
	    for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
		cwavem[ik] = cwave[ik]*rt[ik][im];
#else
		cwavem[ik] = sf_cmul(cwave[ik],rt[ik][im]); /* complex multiplies complex */
#endif
	    }
	    icfft2(wave2[im],cwavem);
	}

/*
	for (im = 0; im < m2; im++) {
	    for (ik = 0; ik < nk; ik++) {
#ifdef SF_HAS_COMPLEX_H
		cwave[ik] = wave[im][ik]*rt[ik][im]*rt[ik][im];
#else
		cwave[ik] = sf_cmul(sf_cmul(wave[im][ik],rt[ik][im]),rt[ik][im]);
#endif
	    }
	    icfft2(wave2[im],cwave);
	}
*/
	for (ix = 0; ix < nx; ix++) {
	    for (iz=0; iz < nz; iz++) {
		i = iz+ix*nz;  /* original grid */
		j = iz+ix*nz2; /* padded grid */
#ifdef SF_HAS_COMPLEX_H
		c = ww[it] * rr[i]; // source term
#else
		c = sf_crmul(ww[it], rr[i]); // source term
#endif
		for (im = 0; im < m2; im++) {
#ifdef SF_HAS_COMPLEX_H
		    c += lt[im][i]*wave2[im][j];
#else
		    c = sf_cadd(c,sf_cmul(lt[im][i], wave2[im][j]));
#endif
		}

		curr[j] = c;
		if (!complx) rcurr[j] = crealf(c);

	    }

	    /* write wavefield to output */
	    if (complx)
		sf_complexwrite(curr+ix*nz2,nz,Fo);
	    else
		sf_floatwrite(rcurr+ix*nz2,nz,Fo);
	}
    }
    if(verb) sf_warning("."); 
    exit (0);
}
Пример #29
0
int main(int argc, char* argv[])
{
    int i, n1, j, n2; 
    int is, ns, iw, nw;
    float d1, d2, dw, ow;
    double omega;
    sf_complex ***wave, ***rhs;
    float **vel;
    double complex neib, cent;
    sf_file in, out, modl;
    int uts, mts;
    char *order;

    sf_init(argc,argv);
    in  = sf_input("in");
    out = sf_output("out");

    if (!sf_getint("uts",&uts)) uts=0;
    /* number of OMP threads */

#ifdef _OPENMP
    mts = omp_get_max_threads();
#else
    mts = 1;
#endif

    uts = (uts < 1)? mts: uts;

    if (NULL == (order = sf_getstring("order"))) order="j";
    /* discretization scheme (default optimal 9-point) */

    /* read model */
    if (NULL == sf_getstring("model"))
	sf_error("Need model=");
    modl = sf_input("model");

    if (!sf_histint(modl,"n1",&n1)) sf_error("No n1=.");
    if (!sf_histint(modl,"n2",&n2)) sf_error("No n2=.");

    if (!sf_histfloat(modl,"d1",&d1)) sf_error("No d1=.");
    if (!sf_histfloat(modl,"d2",&d2)) sf_error("No d2=.");

    vel = sf_floatalloc2(n1,n2);
    sf_floatread(vel[0],n1*n2,modl);

    /* read wavefield */
    if (!sf_histint(in,"n3",&ns)) sf_error("No ns= in input.");
    if (!sf_histint(in,"n4",&nw)) sf_error("No nw= in input.");
    if (!sf_histfloat(in,"d4",&dw)) sf_error("No dw= in input.");
    if (!sf_histfloat(in,"o4",&ow)) sf_error("No ow= in input.");

    wave = sf_complexalloc3(n1,n2,ns);
    
    /* allocate memory */
    rhs = sf_complexalloc3(n1,n2,ns);

    /* loop over frequency */
    for (iw=0; iw < nw; iw++) {
	omega = (double) 2.*SF_PI*(ow+iw*dw);

	sf_complexread(wave[0][0],n1*n2*ns,in);

	/* loop over shots */
#ifdef _OPENMP
#pragma omp parallel for num_threads(uts) private(j,i,neib,cent)
#endif
	for (is=0; is < ns; is++) {
	    switch (order[0]) {
		case '5':
		    for (j=0; j < n2; j++) {
			for (i=0; i < n1; i++) {
			    neib = 0.+I*0.;
			    cent = 0.+I*0.;
			    
			    /* left */
			    if (i > 0)    neib += wave[is][j][i-1]/(d1*d1);
			    cent += -1./(d1*d1);
			    /* right */
			    if (i < n1-1) neib += wave[is][j][i+1]/(d1*d1);
			    cent += -1./(d1*d1);
			    /* down */
			    if (j > 0)    neib += wave[is][j-1][i]/(d2*d2);
			    cent += -1./(d2*d2);
			    /* up */
			    if (j < n2-1) neib += wave[is][j+1][i]/(d2*d2);
			    cent += -1./(d2*d2);
			    /* center */
			    cent += pow(omega/vel[j][i],2.);
			    cent *= wave[is][j][i];
			    
			    rhs[is][j][i] = neib+cent;
			}
		    }
		    break;
		    
		case '9':
		    for (j=0; j < n2; j++) {
			for (i=0; i < n1; i++) {
			    neib = 0.+I*0.;
			    cent = 0.+I*0.;
			    
			    /* left left */
			    if (i > 1)    neib += (-1./12)*wave[is][j][i-2]/(d1*d1);
			    cent += -(-1./12)/(d1*d1);
			    /* left */
			    if (i > 0)    neib += (4./3)*wave[is][j][i-1]/(d1*d1);
			    cent += -(4./3)/(d1*d1);
			    /* right */
			    if (i < n1-1) neib += (4./3)*wave[is][j][i+1]/(d1*d1);
			    cent += -(4./3)/(d1*d1);
			    /* right right */
			    if (i < n1-2) neib += (-1./12)*wave[is][j][i+2]/(d1*d1);
			    cent += -(-1./12)/(d1*d1);
			    /* down down */
			    if (j > 1)    neib += (-1./12)*wave[is][j-2][i]/(d2*d2);
			    cent += -(-1./12)/(d2*d2);
			    /* down */
			    if (j > 0)    neib += (4./3)*wave[is][j-1][i]/(d2*d2);
			    cent += -(4./3)/(d2*d2);
			    /* up */
			    if (j < n2-1) neib += (4./3)*wave[is][j+1][i]/(d2*d2);
			    cent += -(4./3)/(d2*d2);
			    /* up up */
			    if (j < n2-2) neib += (-1./12)*wave[is][j+2][i]/(d2*d2);
			    cent += -(-1./12)/(d2*d2);
			    /* center */
			    cent += pow(omega/vel[j][i],2.);
			    cent *= wave[is][j][i];
			    
			    rhs[is][j][i] = neib+cent;
			}
		    }
		    break;
		    
		case 'j':
		    for (j=0; j < n2; j++) {
			for (i=0; i < n1; i++) {
			    neib = 0.+I*0.;
			    cent = 0.+I*0.;
			    
			    /* left */
			    if (i > 0)
				neib += (0.7926/(d1*d1)-
					 0.1037/(d2*d2)-
					 0.1037/(d2*d2)+
					 0.0942*pow(omega/vel[j][i-1],2.))*
				    wave[is][j][i-1];
			    cent += -0.7926/(d1*d1);
			    /* right */
			    if (i < n1-1)
				neib += (0.7926/(d1*d1)-
					 0.1037/(d2*d2)-
					 0.1037/(d2*d2)+
					 0.0942*pow(omega/vel[j][i+1],2.))*
				    wave[is][j][i+1];
			    cent += -0.7926/(d1*d1);
			    /* down */
			    if (j > 0)
				neib += (0.7926/(d2*d2)-
					 0.1037/(d1*d1)-
					 0.1037/(d1*d1)+
					 0.0942*pow(omega/vel[j-1][i],2.))*
				    wave[is][j-1][i];
			    cent += -0.7926/(d2*d2);
			    /* up */
			    if (j < n2-1)
				neib += (0.7926/(d2*d2)-
					 0.1037/(d1*d1)-
					 0.1037/(d1*d1)+
					 0.0942*pow(omega/vel[j+1][i],2.))*
				    wave[is][j+1][i];
			    cent += -0.7926/(d2*d2);
			    /* left down */
			    if (i > 0 && j > 0)
				neib += (0.1037/(d1*d1)+
					 0.1037/(d2*d2)-
					 0.0016*pow(omega/vel[j-1][i-1],2.))*
				    wave[is][j-1][i-1];
			    /* right up */
			    if (i < n1-1 && j < n2-1)
				neib += (0.1037/(d1*d1)+
					 0.1037/(d2*d2)-
					 0.0016*pow(omega/vel[j+1][i+1],2.))*
				    wave[is][j+1][i+1];
			    /* left up */
			    if (i > 0 && j < n2-1)
				neib += (0.1037/(d1*d1)+
					 0.1037/(d2*d2)-
					 0.0016*pow(omega/vel[j+1][i-1],2.))*
				    wave[is][j+1][i-1];
			    /* right down */
			    if (i < n1-1 && j > 0)
				neib += (0.1037/(d1*d1)+
					 0.1037/(d2*d2)-
					 0.0016*pow(omega/vel[j-1][i+1],2.))*
				    wave[is][j-1][i+1];
			    /* center */
			    cent += 0.6296*pow(omega/vel[j][i],2.);
			    cent *= wave[is][j][i];
			    
			    rhs[is][j][i] = neib+cent;
			}
		    }
		    break;
		    
		case 'c':
		    for (j=0; j < n2; j++) {
			for (i=0; i < n1; i++) {
			    neib = 0.+I*0.;
			    cent = 0.+I*0.;
			    
			    /* left up */
			    if (i > 0 && j > 0)
				neib += (0.06181325/(d1*d1)+
					 0.06181325/(d2*d2)+
					 0.0424801*pow(omega/vel[j-1][i-1],2.))*
				    wave[is][j-1][i-1];
			    /* up */
			    if (i > 0)
				neib += (0.2880195/(d1*d1)-
					 0.06181325/(d2*d2)-
					 0.06181325/(d2*d2)-
					 0.1389664/(4.*d2*d2)-
					 0.1389664/(4.*d2*d2)+
					 0.108598*pow(omega/vel[j][i-1],2.))*
				    wave[is][j][i-1];
			    cent += -0.2880195/(d1*d1);
			    /* right up */
			    if (i > 0 && j < n2-1)
				neib += (0.06181325/(d1*d1)+
					 0.06181325/(d2*d2)+
					 0.0424801*pow(omega/vel[j+1][i-1],2.))*
				    wave[is][j+1][i-1];
			    /* right */
			    if (j < n2-1)
				neib += (0.2880195/(d2*d2)-
					 0.06181325/(d1*d1)-
					 0.06181325/(d1*d1)-
					 0.1389664/(4.*d1*d1)-
					 0.1389664/(4.*d1*d1)+
					 0.108598*pow(omega/vel[j+1][i],2.))*
				    wave[is][j+1][i];
			    cent += -0.2880195/(d2*d2);
			    /* right down */
			    if (i < n1-1 && j < n2-1)
				neib += (0.06181325/(d1*d1)+
					 0.06181325/(d2*d2)+
					 0.0424801*pow(omega/vel[j+1][i+1],2.))*
				    wave[is][j+1][i+1];
			    /* down */
			    if (i < n1-1)
				neib += (0.2880195/(d1*d1)-
					 0.06181325/(d2*d2)-
					 0.06181325/(d2*d2)-
					 0.1389664/(4.*d2*d2)-
					 0.1389664/(4.*d2*d2)+
					 0.108598*pow(omega/vel[j][i+1],2.))*
				    wave[is][j][i+1];
			    cent += -0.2880195/(d1*d1);
			    /* left down */
			    if (i < n1-1 && j > 0)
				neib += (0.06181325/(d1*d1)+
					 0.06181325/(d2*d2)+
					 0.0424801*pow(omega/vel[j-1][i+1],2.))*
				    wave[is][j-1][i+1];
			    /* left */
			    if (j > 0)
				neib += (0.2880195/(d2*d2)-
					 0.06181325/(d1*d1)-
					 0.06181325/(d1*d1)-
					 0.1389664/(4.*d1*d1)-
					 0.1389664/(4.*d1*d1)+
					 0.108598*pow(omega/vel[j-1][i],2.))*
				    wave[is][j-1][i];
			    cent += -0.2880195/(d2*d2);
			    /* left left up up */
			    if (i > 1 && j > 1)
				neib += (0.007436025/(4.*d1*d1)+
					 0.007436025/(4.*d2*d2)+
					 0.000206312*pow(omega/vel[j-2][i-2],2.))*
				    wave[is][j-2][i-2];
			    /* left up up */
			    if (i > 1 && j > 0)
				neib += (0.1389664/(4.*d1*d1)+
					 0.00188342*pow(omega/vel[j-1][i-2],2.))*
				    wave[is][j-1][i-2];
			    /* up up */
			    if (i > 1)
				neib += (0.29554905/(4.*d1*d1)-
					 0.007436025/(4.*d2*d2)-
					 0.007436025/(4.*d2*d2)+
					 0.0041487*pow(omega/vel[j][i-2],2.))*
				    wave[is][j][i-2];
			    cent += -0.29554905/(4.*d1*d1);
			    /* right up up */
			    if (i > 1 && j < n2-1)
				neib += (0.1389664/(4.*d1*d1)+
					 0.00187765*pow(omega/vel[j+1][i-2],2.))*
				    wave[is][j+1][i-2];
			    /* right right up up */
			    if (i > 1 && j < n2-2)
				neib += (0.007436025/(4.*d1*d1)+
					 0.007436025/(4.*d2*d2)+
					 0.000206312*pow(omega/vel[j+2][i-2],2.))*
				    wave[is][j+2][i-2];
			    /* right right up */
			    if (i > 0 && j < n2-2)
				neib += (0.1389664/(4.*d2*d2)+
					 0.00188342*pow(omega/vel[j+2][i-1],2.))*
				    wave[is][j+2][i-1];
			    /* right right */
			    if (j < n2-2)
				neib += (0.29554905/(4.*d2*d2)-
					 0.007436025/(4.*d1*d1)-
					 0.007436025/(4.*d1*d1)+
					 0.0041487*pow(omega/vel[j+2][i],2.))*
				    wave[is][j+2][i];
			    cent += -0.29554905/(4.*d2*d2);
			    /* right right down */
			    if (i < n1-1 && j < n2-2)
				neib += (0.1389664/(4.*d2*d2)+
					 0.00187765*pow(omega/vel[j+2][i+1],2.))*
				    wave[is][j+2][i+1];
			    /* right right down down */
			    if (i < n1-2 && j < n2-2)
				neib += (0.007436025/(4.*d1*d1)+
					 0.007436025/(4.*d2*d2)+
					 0.000206312*pow(omega/vel[j+2][i+2],2.))*
				    wave[is][j+2][i+2];
			    /* right down down */
			    if (i < n1-2 && j < n2-1)
				neib += (0.1389664/(4.*d1*d1)+
					 0.00188342*pow(omega/vel[j+1][i+2],2.))*
				    wave[is][j+1][i+2];
			    /* down down */
			    if (i < n1-2)
				neib += (0.29554905/(4.*d1*d1)-
					 0.007436025/(4.*d2*d2)-
					 0.007436025/(4.*d2*d2)+
					 0.0041487*pow(omega/vel[j][i+2],2.))*
				    wave[is][j][i+2];
			    cent += -0.29554905/(4.*d1*d1);
			    /* left down down */
			    if (i < n1-2 && j > 0)
				neib += (0.1389664/(4.*d1*d1)+
					 0.00187765*pow(omega/vel[j-1][i+2],2.))*
				    wave[is][j-1][i+2];
			    /* left left down down */
			    if (i < n1-2 && j > 1)
				neib += (0.007436025/(4.*d1*d1)+
					 0.007436025/(4.*d2*d2)+
					 0.000206312*pow(omega/vel[j-2][i+2],2.))*
				    wave[is][j-2][i+2];
			    /* left left down */
			    if (i < n1-1 && j > 1)
				neib += (0.1389664/(4.*d2*d2)+
					 0.00188342*pow(omega/vel[j-2][i+1],2.))*
				    wave[is][j-2][i+1];
			    /* left left */
			    if (j > 1)
				neib += (0.29554905/(4.*d2*d2)-
					 0.007436025/(4.*d1*d1)-
					 0.007436025/(4.*d1*d1)+
					 0.0041487*pow(omega/vel[j-2][i],2.))*
				    wave[is][j-2][i];
			    cent += -0.29554905/(4.*d2*d2);
			    /* left left up */
			    if (i > 0 && j > 1)
				neib += (0.1389664/(4.*d2*d2)+
					 0.00187765*pow(omega/vel[j-2][i-1],2.))*
				    wave[is][j-2][i-1];
			    /* center */
			    cent += 0.363276*pow(omega/vel[j][i],2.);
			    cent *= wave[is][j][i];
			    
			    rhs[is][j][i] = neib+cent;
			}
		    }
		    break;
		    
		default:
		    sf_error("Fail to load discretization scheme.");
	    }
	}

	sf_complexwrite(rhs[0][0],n1*n2*ns,out);
    }
    
    exit(0);
}
Пример #30
0
int main(int argc, char* argv[])
{
    bool sorted;
    int i1, n1, i2, n2, ip, np;
    float o1, d1, t0, t1, t2, t, a, *trace=NULL;
    float min, max, x;
    sf_complex *pick=NULL;
    sf_file in=NULL, out=NULL;

    sf_init(argc, argv);
    in = sf_input("in");
    out = sf_output("out");

    if (!sf_histint(in,"n1",&n1)) sf_error("No n1= in input");
    n2 = sf_leftsize(in,1);

    if (!sf_histfloat(in,"d1",&d1)) d1=1.;
    if (!sf_histfloat(in,"o1",&o1)) o1=0.;

    if (!sf_getfloat("min",&min)) min=o1;
    /* minimum value of time */

    if (!sf_getfloat("max",&max)) max=o1+(n1-1)*d1; 
    /* maximum value of time */ 

    if (!sf_getint("np",&np)) np=n1;
    /* maximum number of picks */

    if (!sf_getbool("sorted",&sorted)) sorted=true;
    /* if y, sort by amplitude */

    sf_putint(out,"n1",np);
    sf_settype(out,SF_COMPLEX);

    trace = sf_floatalloc(n1);
    pick = sf_complexalloc(np);

    for (i2=0; i2 < n2; i2++) {
	sf_floatread(trace,n1,in);

	t0 = trace[0];
	t1 = trace[1];
	ip = 0;
	for (i1=2; i1 < n1; i1++) {
	    t2 = trace[i1];
	    
	    if (ip < np && t1 > t0 && t1 > t2) {
		/* parabolic approximation */
		t = 0.5*(t2-t0)/(2*t1-t0-t2);
		a = t1+0.25*(t2-t0)*t;

		if (t < -1.) {
		    t=-1;
		    a=t0;
		} else if (t > 1.) {
		    t=1.;
		    a=t2;
		} 

		x = o1+(i1-1+t)*d1;

		if (x >= min && x <= max) {
		    pick[ip] = sf_cmplx(x,a);	
		    ip++;
		}
	    }

	    t0 = t1;
	    t1 = t2;
	}

	if (0==ip) {
	    pick[0] = sf_cmplx(o1-d1,0.);
	    ip++;
	}

	if (sorted) qsort(pick,ip,sizeof(sf_complex),pick_compare);
	
	for (i1=ip; i1 < np; i1++) {
	    pick[i1] = sf_cmplx(crealf(pick[ip-1]),0.);
	}

	sf_complexwrite(pick,np,out);
    }

    exit(0);
}