void inmo_oper(int nx, const float *trace, float *trace2, void* user_data) /*< operator to invert by GMRES >*/ { int it; /* forward operator */ inmo(trace,dense2); subsample(dense2,sparse2); /* backward operator */ interpolate(sparse2,dense2); nmostack(dense2,trace2); /* I + S (BF - I) */ for (it=0; it < nt; it++) { trace2[it] -= trace[it]; } bandpass(trace2); for (it=0; it < nt; it++) { trace2[it] += trace[it]; } }
int main (int argc, char* argv[]) { bool half, slow; int ih,ix,it,nt,nx,nd,nh, CDPtype, jump, niter, restart, nplo, nphi, ni, axis,lim,j; off_t n; float dt, t0, h0, dh, eps, dy, tol, flo, fhi; float *trace, *trace2, *vel, *off, **gather, **dense; char key1[7]; sf_file cmp, stack, velocity, offset; sf_init (argc,argv); cmp = sf_input("in"); velocity = sf_input("velocity"); stack = sf_output("out"); axis = 2; lim = axis-1; n = 1; for (j=0; j < lim; j++) { sprintf(key1,"n%d",j+1); if (!sf_histint(cmp,key1,&ni)) break; n *= ni; } (void) sf_unshiftdim(cmp,stack,axis); if (SF_FLOAT != sf_gettype(cmp)) sf_error("Need float input"); if (!sf_histint(cmp,"n1",&nt)) sf_error("No n1= in input"); if (!sf_histfloat(cmp,"d1",&dt)) sf_error("No d1= in input"); if (!sf_histfloat(cmp,"o1",&t0)) sf_error("No o1= in input"); if (!sf_histint(cmp,"n2",&nh)) sf_error("No n2= in input"); off = sf_floatalloc(nh); if (!sf_getbool("half",&half)) half=true; /* if y, the second axis is half-offset instead of full offset */ CDPtype=1; if (NULL != sf_getstring("offset")) { offset = sf_input("offset"); sf_floatread (off,nh,offset); sf_fileclose(offset); } else { if (!sf_histfloat(cmp,"d2",&dh)) sf_error("No d2= in input"); if (!sf_histfloat(cmp,"o2",&h0)) sf_error("No o2= in input"); if (sf_histfloat(cmp,"d3",&dy)) { CDPtype=half? 0.5+dh/dy : 0.5+0.5*dh/dy; if (CDPtype < 1) { CDPtype=1; } else if (1 != CDPtype) { sf_histint(cmp,"CDPtype",&CDPtype); sf_warning("CDPtype=%d",CDPtype); } } for (ih = 0; ih < nh; ih++) { off[ih] = h0 + ih*dh; } } if (!sf_getbool("slowness",&slow)) slow=false; /* if y, use slowness instead of velocity */ nx = sf_leftsize(cmp,2); if (!sf_getfloat ("h0",&h0)) h0=0.; /* reference offset */ if (half) h0 *= 2.; if (!sf_getfloat("eps",&eps)) eps=0.01; /* stretch regularization */ if (!sf_getint("jump",&jump)) jump=1; /* subsampling */ if (!sf_getint("niter",&niter)) niter=10; /* number of iterations */ if (!sf_getint("restart",&restart)) restart=niter; /* GMRES memory */ if (!sf_getfloat("tol",&tol)) tol=1e-5; /* GMRES tolerance */ if (!sf_getfloat("flo",&flo)) { /* Low frequency in band, default is 0 */ flo=0.; } else if (0. > flo) { sf_error("Negative flo=%g",flo); } else { flo *= (dt/jump); } if (!sf_getfloat("fhi",&fhi)) { /* High frequency in band, default is Nyquist */ fhi=0.5; } else { fhi *= (dt/jump); if (flo > fhi) sf_error("Need flo < fhi, " "got flo=%g, fhi=%g",flo/(dt/jump),fhi/(dt/jump)); if (0.5 < fhi) sf_error("Need fhi < Nyquist, " "got fhi=%g, Nyquist=%g",fhi/(dt/jump),0.5/(dt/jump)); } if (!sf_getint("nplo",&nplo)) nplo = 6; /* number of poles for low cutoff */ if (nplo < 1) nplo = 1; if (nplo > 1) nplo /= 2; if (!sf_getint("nphi",&nphi)) nphi = 6; /* number of poles for high cutoff */ if (nphi < 1) nphi = 1; if (nphi > 1) nphi /= 2; nd = (nt-1)*jump+1; bandpass_init(nd,flo,fhi,nplo,nphi); sf_putint(stack,"n1",nd); sf_putfloat(stack,"d1",dt/jump); trace = sf_floatalloc(nd); trace2 = sf_floatalloc(nd); gather = sf_floatalloc2(nt,nh); dense = sf_floatalloc2(nd,nh); vel = sf_floatalloc(nd); for (ix = 0; ix < nx; ix++) { /* loop over midpoint nx*/ sf_floatread (vel,nd,velocity); inmo_init(vel, off, nh, h0, dh, CDPtype, ix, nt, slow, t0, dt, eps, half, jump); sf_floatread (gather[0],nt*nh,cmp); /* apply backward operator */ interpolate(gather, dense); nmostack(dense,trace); /* apply shaping */ bandpass(trace); sf_gmres_init(nd,restart); for (it=0; it < nd; it++) { trace2[it] = 0.0f; } /* run GMRES */ sf_gmres(trace,trace2,inmo_oper,NULL,niter,tol,true); sf_floatwrite (trace2,nd,stack); sf_gmres_close(); inmo_close(); } exit (0); }
FramePtr Demodulator::decode(const FrameAudio& frame_audio) { QVector<double> buffer; buffer.reserve(frame_audio.count()); FIRFilter bandpass(FIRFilter::FIR_BANDPASS, settings_.window, SAMPLING_RATE, 220, 900, 2500); FIRFilter lowpass(FIRFilter::FIR_LOWPASS, settings_.window, 528000, 12000, SAMPLING_RATE / 2); int index = 0; for (double value : frame_audio) { double low = lowpass.process(value); if (index % 40 == 0) { buffer.push_back(bandpass.process(low)); } index++; for (int i = 0; i < 10; ++i) { low = lowpass.process(0); if (index % 40 == 0) { buffer.push_back(bandpass.process(low)); } index++; } } RingBuffer<double> bufs1200(BITS_PER_BYTE); RingBuffer<double> bufc1200(BITS_PER_BYTE); RingBuffer<double> bufs2200(BITS_PER_BYTE); RingBuffer<double> bufc2200(BITS_PER_BYTE); QVector<double> diff_buff; for (int i = 0; i < buffer.size(); ++i) { bufs1200.push_back(sin(M_PI * 2 / SAMPLING_RATE * 1200.0 * i) * buffer[i]); bufc1200.push_back(cos(M_PI * 2 / SAMPLING_RATE * 1200.0 * i) * buffer[i]); bufs2200.push_back(sin(M_PI * 2 / SAMPLING_RATE * 2200.0 * i) * buffer[i]); bufc2200.push_back(cos(M_PI * 2 / SAMPLING_RATE * 2200.0 * i) * buffer[i]); double low = std::hypotf(bufs1200.sum(), bufc1200.sum()); double high = std::hypotf(bufs2200.sum() , bufc2200.sum()); diff_buff.push_back(low - high); } QVector<double> diff_buff_center = diff_buff; qSort(diff_buff_center); double min = diff_buff_center[diff_buff_center.size() / 4]; double max = diff_buff_center[diff_buff_center.size() / 4 + diff_buff_center.size() / 2]; double center = diff_buff_center[diff_buff_center.size() / 2]; for (int i = 0; i <= THRESHOLD_RESOLUTION; ++i) { FramePtr frame; process(settings_.verfy_fcs, center - std::fabs(center - min / THRESHOLD_WIDTH_RATIO) * (1.0 * i / THRESHOLD_RESOLUTION), diff_buff, &frame); if (frame) { return frame; } process(settings_.verfy_fcs, center + std::fabs(center - max / THRESHOLD_WIDTH_RATIO) * (1.0 * i / THRESHOLD_RESOLUTION), diff_buff, &frame); if (frame) { return frame; } } return FramePtr(); }
main(int argc, char **argv) { float **filter; /* filter arrays */ float *tf; /* times at which filters are centered */ int *itf; /* ... as integers */ int jmin; /* index of first filter itf value */ int jmax; /* index of last filter itf value */ int nfft; /* fft sizes in each time gate */ int nfreq; /* number of frequencies */ float **ftrace; /* filtered sub-traces */ int nfilter; /* number of filters specified */ float dt; /* sample spacing */ float tmin; /* first time on traces */ int nt; /* number of points on input trace */ float *data; FILE *infp=stdin, *outfp=stdout; /* Initialize */ initargs(argc, argv); requestdoc(1); /* Get info from first trace */ file2g(infp); file2g(outfp); if (!fgettr(infp,&tr)) err("can't get first trace"); if (tr.trid && tr.trid != TREAL) err("input is not seismic data, trid=%d", tr.trid); nt = tr.ns; if (!getparfloat("dt", &dt)) dt = (float)tr.dt/1000000.0; if (!dt) err("dt field is zero and not getparred"); tmin = tr.delrt/1000.0; /* Get number of filters and center times */ if (!(nfilter = countparval("tf"))) MUSTGETPARFLOAT("tf", tf); if (countparname("f") != nfilter) err("must give one f 4-tuple for each" " (%d) tf value", nfilter); /* Leave room for possibly missing filters at endpoints */ tf = ealloc1float(nfilter+4); /* never use ist2 or last 2 */ itf = ealloc1int(nfilter+4); getparfloat("tf", tf+2); jmin = 2; jmax = nfilter + 1; { register int j; for (j = jmin; j <= jmax; ++j) itf[j] = NINT((tf[j] - tmin)/dt); } /* Make filters with scale for inverse transform */ nfft = npfaro(nt, LOOKFAC * nt); if (nfft >= MIN(SU_NFLTS, PFA_MAX)) err("Padded nt=%d -- too big", nfft); nfreq = nfft/2 + 1; filter = ealloc2float(nfreq, nfilter+4); /* never use 1st & last */ { register int j; for (j = jmin; j <= jmax; ++j) { float *f = ealloc1float(4); if (getnparfloat(j-jmin+1, "f", f) != 4) err("must give 4 corner frequencies in f="); if (f[0] < 0.0 || f[0] > f[1] || f[1] >= f[2] || f[2] > f[3]) err("Filter #%d has bad frequencies", j - jmin + 1); makefilter(f, nfft, nfreq, dt, filter[j]); } } /* User may not have given a filter for tmin and/or tmax-- */ /* Extend array so can always assume these filters are present. */ /* Note don't really use any of the extra storage in **filter! */ if (itf[jmin] > 0) { filter[jmin-1] = filter[jmin]; itf[jmin-1] = 0; --jmin; } if (itf[jmax] < nt - 1) { filter[jmax+1] = filter[jmax]; itf[jmax+1] = nt - 1; ++jmax; } /* Extend array so can always consider time points to be interior */ itf[jmin-1] = 0; /* now jmin - 1 is a valid index */ itf[jmax+1] = nt - 1; /* now jmax + 1 is a valid index */ /* Main loop over traces */ ftrace = ealloc2float(nt, nfilter+4); /* never use 1st & last */ data = ealloc1float(nt); do { register int i, j; /* Construct filtered sub-traces */ for (j = jmin; j <= jmax; ++j) { bzero(data, nt*FSIZE); for (i = itf[j-1]; i <= itf[j+1]; ++i) data[i] = tr.data[i]; bandpass(data,nt,nfft,nfreq,filter[j],ftrace[j]); } /* Compose filtered trace from sub-traces */ for (j = jmin; j < jmax; ++j) { float fitfj; for (fitfj = i = itf[j]; i <= itf[j+1]; ++i) { float a = (i - fitfj)/(itf[j+1] - fitfj); tr.data[i] = (1-a)*ftrace[j][i] + a*ftrace[j+1][i]; } } fputtr(outfp,&tr); } while (fgettr(infp,&tr)); return EXIT_SUCCESS; }