/* JRG, the Resource Geology Seismic Processing System for Java, and Viewmat for Java are Copyright 1998-2000 by John N. Louie The software and methods here are the subject of academic research, not commercial products. I would like to know what use you make of my methods, and have your feedback on their success or failure. Also, by letting me know who you are, I can inform you if bugs or errors are discovered. Please send me an email message with: your name and email address; whether you are a student or faculty member, consultant or employee; the name of your university or company, and department; and a sentence or two describing what use you intend to make of these methods. Send your message to louie@seismo.unr.edu */ import java.io.*; public class SEGYTraceHead /* standard SEG-Y trace */ { public static int SEGY_THEAD_SIZE=3600; /* segy tape header blocks total in bytes */ public static int SEGY_HEAD_SIZE=240; /* segy header size in bytes */ public static int MSK_MANT_IBM=0xffffff; public static int MSK_EXP_IBM=0x7f000000; public static int MSK_SIGN_IBM=0x80000000; public static int MSK_NORM_IEEE=0x800000; public static int MSK_NO_SIGN=0x7fffffff; public int trseql; /* 0: trace sequence no. in line */ public int trseqr; /* 4: trace sequence no. in reel */ public int frecno; /* 8: original field record no. */ public int trnof; /* 12: trace no. within original field rec */ public int sp; /* 16: energy source point number */ public int cdpensno; /* 20: CDP ensemble no. */ public int enstrno; /* 24: trace number within CDP ensemble */ public short trid; /* 28: trace id code */ public short vsumno; /* 30: no. of vertically summed traces in trace */ public short hsumno; /* 32: no. of horizontally summed traces in trace */ public short use; /* 34: data use */ public int offset; /* 36: distance from source point to receiver */ public int gz; /* 40: elevation of receiver group */ public int szsurf; /* 44: surface elevation at source */ public int sdepth; /* 48: source depth below surface */ public int gdatz; /* 52: datum elevation at receiver group */ public int sdatz; /* 56: datum elevation at source */ public int swatdep; /* 60: water depth at source */ public int gwatdep; /* 64: water depth at receiver group */ public short lscaler; /* 68: elevation and depth scaler */ public short coscaler; /* 70: coordinate scaler */ public int sx; /* 72: x source coordinate */ public int sy; /* 76: y source coordinate */ public int gx; /* 80: x receiver group coordinate */ public int gy; /* 84: y receiver group coordinate */ public short counit; /* 88: coordinate units */ public short vweath; /* weathering velocity */ public short vsbweath; /* subweathering velocity */ public short tus; /* uphole time at source */ public short tug; /* uphole time at receiver group */ public short dts; /* source static correction */ public short dtg; /* receiver group static correction */ public short dttotal; /* total static applied */ public short tlA; /* lag time A */ public short tlB; /* lag time B */ public short delay; /* recording delay time */ public short tmute0; /* mute time start */ public short tmutef; /* mute time end */ public short nt; /* 114: no. of samples in trace */ public short dt; /* sample interval in trace */ public short gaintype; /* gain type of field instruments */ public short kgain; /* instrument gain constant */ public short gain0; /* instrument early or initial gain */ public short correl; /* correlation switch */ public short swf0; /* sweep frequency at start */ public short swff; /* sweep frequency at end */ public short swt; /* sweep length */ public short swtype; /* sweep type */ public short swtrtpt0; /* sweep trace taper length at start */ public short swtrtptf; /* sweep trace taper length at end */ public short swtaptype;/* sweep taper type */ public short alff; /* alias filter frequency */ public short alfsl; /* alias filter slope */ public short nchff; /* notch filter frequency */ public short nchfsl; /* notch filter slope */ public short lcf; /* low cut frequency */ public short hcf; /* high cut frequency */ public short lcsl; /* low cut slope */ public short hcsl; /* high cut slope */ public short year; /* year data recorded */ public short jday; /* day of year */ public short hour; /* hour of day */ public short minute; /* minute of hour */ public short second; /* second of minute */ public short tbasis; /* time basis code */ public short trwt; /* trace weighting factor */ public short rsw1gno; /* geophone group no. of roll switch pos. 1 */ public short frtr1gno; /* grp. no. of trace 1 w/i orig. field rec. */ public short frtrfgno; /* grp. no. of last trace w/i field rec. */ public short gapsize; /* gap size */ public short overtrav; /* overtravel assoc. w/ taper at line ends */ public int fdt; /* (IBM float) floating residual static correction */ public int fdts; /* (IBM float) floating residual shot static */ public int fdtg; /* (IBM float) floating residual receiver static */ public int fdtd; /* (IBM float) floating residual depthpoint static */ public int fdtmo; /* (IBM float) floating residual moveout static */ /*public byte unas[];*/ /* unassigned */ /* Use PASSCAL assignments for unasigned SEG-Y fields: */ public int samp_rate; /* long ints in PASSCAL decls for Sun are 4-byte */ public short data_form, m_secs; public short trigyear,trigday,trighour,trigminute,trigsecond,trigmills; public float scale_fac; /* IEEE float */ /* scale_fac == 0F signifies no valid scale factor */ public short inst_no; public short not_to_be_used; public int num_samps; public int max; public int min; public int getnt() { if ((nt < 1 || nt >= (short)(32767)) && num_samps > 0 && num_samps < 2000000000) return num_samps; else return nt; } public void setnt(int n) { if (n >= 32767) nt = (short)(32767); else nt = (short)(n); num_samps = n; } public void copyRgFileHead(RgFileHead fhd) { /*this.nt = (short)(fhd.nt);*/ this.setnt(fhd.nt); this.dt = (short)(1e6F*fhd.dt); this.delay = (short)(1e3F*fhd.starttime); } public void copyRgHead(RgHead rgthd, RgFileHead fhd, int itrace, double lscl, double coscl, boolean geogr) { if (lscl < 0) lscl = -lscl; if (coscl < 0) coscl = -coscl; if (lscl < 1) this.lscaler = (short)(-1/lscl); if (coscl < 1) this.coscaler = (short)(-1/coscl); if (geogr) this.counit = (short)(2); else this.counit = (short)(1); this.frecno = rgthd.rec; /*this.nt = (short)(fhd.nt);*/ this.setnt(fhd.nt); this.dt = (short)(1e6F*fhd.dt); this.delay = (short)(1e3F*fhd.starttime); this.sx = (int)(rgthd.sx/coscl); this.sy = (int)(rgthd.sy/coscl); this.szsurf = (int)(rgthd.sz/lscl); this.sdepth = 0; this.gdatz = 0; this.sdatz = 0; this.gx = (int)(rgthd.gx/coscl); this.gy = (int)(rgthd.gy/coscl); this.gz = (int)(rgthd.gz/lscl); this.offset = (int)(rgthd.off); this.sp = rgthd.svp; this.trnof = (short)(itrace+1); this.rsw1gno = (short)(rgthd.gvp - itrace); this.frtr1gno = (short)(rgthd.gvp - itrace); this.frtrfgno = (short)(rgthd.gvp - itrace + fhd.ntrace); this.gapsize = (short)(0); overtrav = (short)(0); } public void copyRgHead(RgHead rgthd, RgFileHead fhd, int itrace) { copyRgHead(rgthd, fhd, itrace, 1, 1, false); } public boolean isValid() { if (trseql < 1 || trseqr < 1 || frecno < 0 || trid < (short)(0) /*|| nt < (short)(1)*/ || getnt() < 1 || getnt() > 2000000000 || dt < (short)(1)) return false; return true; } public boolean isGeogr() { if (coscaler == (short)(-3600) || counit == (short)(2)) return true; return false; } public void regularize() { if (trid == (short)(0)) trid = (short)(1); if (lscaler == (short)(0)) lscaler = (short)(1); if (coscaler == (short)(0)) coscaler = (short)(1); if (counit == (short)(0)) counit = (short)(1); if (tbasis == (short)(0)) tbasis = (short)(1); if (vsumno == (short)(0)) vsumno = (short)(1); if (hsumno == (short)(0)) hsumno = (short)(1); if (use == (short)(0)) use = (short)(1); if (correl == (short)(0)) correl = (short)(1); } /*Constructor*/ SEGYTraceHead() { trseql = 1; trseqr = 1; frecno = 1; trnof = 1; enstrno = 1; trid = (short)(1); vsumno = (short)(1); hsumno = (short)(1); use = (short)(1); lscaler = (short)(1); coscaler = (short)(1); counit = (short)(1); correl = (short)(1); tbasis = (short)(1); /*unas = new byte[40];*/ } /* Construct a copy */ SEGYTraceHead(SEGYTraceHead hd) { this.alff = hd.alff; this.alfsl = hd.alfsl; this.cdpensno = hd.cdpensno; this.correl = hd.correl; this.coscaler = hd.coscaler; this.counit = hd.counit; this.delay = hd.delay; this.dt = hd.dt; this.dtg = hd.dtg; this.dts = hd.dts; this.dttotal = hd.dttotal; this.enstrno = hd.enstrno; this.fdt = hd.fdt; this.fdtd = hd.fdtd; this.fdtg = hd.fdtg; this.fdtmo = hd.fdtmo; this.fdts = hd.fdts; this.frecno = hd.frecno; this.frtr1gno = hd.frtr1gno; this.frtrfgno = hd.frtrfgno; this.gain0 = hd.gain0; this.gaintype = hd.gaintype; this.gapsize = hd.gapsize; this.gdatz = hd.gdatz; this.gwatdep = hd.gwatdep; this.gx = hd.gx; this.gy = hd.gy; this.gz = hd.gz; this.hcf = hd.hcf; this.hcsl = hd.hcsl; this.hour = hd.hour; this.hsumno = hd.hsumno; this.jday = hd.jday; this.kgain = hd.kgain; this.lcf = hd.lcf; this.lcsl = hd.lcsl; this.lscaler = hd.lscaler; this.minute = hd.minute; this.nchff = hd.nchff; this.nchfsl = hd.nchfsl; this.nt = hd.nt; this.offset = hd.offset; this.overtrav = hd.overtrav; this.rsw1gno = hd.rsw1gno; this.sdatz = hd.sdatz; this.sdepth = hd.sdepth; this.second = hd.second; this.sp = hd.sp; this.swatdep = hd.swatdep; this.swf0 = hd.swf0; this.swff = hd.swff; this.swt = hd.swt; this.swtaptype = hd.swtaptype; this.swtrtpt0 = hd.swtrtpt0; this.swtrtptf = hd.swtrtptf; this.swtype = hd.swtype; this.sx = hd.sx; this.sy = hd.sy; this.szsurf = hd.szsurf; this.tbasis = hd.tbasis; this.tlA = hd.tlA; this.tlB = hd.tlB; this.tmute0 = hd.tmute0; this.tmutef = hd.tmutef; this.trid = hd.trid; this.trnof = hd.trnof; this.trseql = hd.trseql; this.trseqr = hd.trseqr; this.trwt = hd.trwt; this.tug = hd.tug; this.tus = hd.tus; this.use = hd.use; this.vsbweath = hd.vsbweath; this.vsumno = hd.vsumno; this.vweath = hd.vweath; this.year = hd.year; /* for (int i=0; i<40; i++) this.unas[i] = hd.unas[i]; */ this.samp_rate = hd.samp_rate; this.data_form = hd.data_form; this.m_secs = hd.m_secs; this.trigyear = hd.trigyear; this.trigday = hd.trigday; this.trighour = hd.trighour; this.trigminute = hd.trigminute; this.trigsecond = hd.trigsecond; this.trigmills = hd.trigmills; this.scale_fac = hd.scale_fac; this.inst_no = hd.inst_no; this.not_to_be_used = hd.not_to_be_used; this.num_samps = hd.num_samps; this.max = hd.max; this.min = hd.min; } public void copy(SEGYTraceHead hd) { this.alff = hd.alff; this.alfsl = hd.alfsl; this.cdpensno = hd.cdpensno; this.correl = hd.correl; this.coscaler = hd.coscaler; this.counit = hd.counit; this.delay = hd.delay; this.dt = hd.dt; this.dtg = hd.dtg; this.dts = hd.dts; this.dttotal = hd.dttotal; this.enstrno = hd.enstrno; this.fdt = hd.fdt; this.fdtd = hd.fdtd; this.fdtg = hd.fdtg; this.fdtmo = hd.fdtmo; this.fdts = hd.fdts; this.frecno = hd.frecno; this.frtr1gno = hd.frtr1gno; this.frtrfgno = hd.frtrfgno; this.gain0 = hd.gain0; this.gaintype = hd.gaintype; this.gapsize = hd.gapsize; this.gdatz = hd.gdatz; this.gwatdep = hd.gwatdep; this.gx = hd.gx; this.gy = hd.gy; this.gz = hd.gz; this.hcf = hd.hcf; this.hcsl = hd.hcsl; this.hour = hd.hour; this.hsumno = hd.hsumno; this.jday = hd.jday; this.kgain = hd.kgain; this.lcf = hd.lcf; this.lcsl = hd.lcsl; this.lscaler = hd.lscaler; this.minute = hd.minute; this.nchff = hd.nchff; this.nchfsl = hd.nchfsl; this.nt = hd.nt; this.offset = hd.offset; this.overtrav = hd.overtrav; this.rsw1gno = hd.rsw1gno; this.sdatz = hd.sdatz; this.sdepth = hd.sdepth; this.second = hd.second; this.sp = hd.sp; this.swatdep = hd.swatdep; this.swf0 = hd.swf0; this.swff = hd.swff; this.swt = hd.swt; this.swtaptype = hd.swtaptype; this.swtrtpt0 = hd.swtrtpt0; this.swtrtptf = hd.swtrtptf; this.swtype = hd.swtype; this.sx = hd.sx; this.sy = hd.sy; this.szsurf = hd.szsurf; this.tbasis = hd.tbasis; this.tlA = hd.tlA; this.tlB = hd.tlB; this.tmute0 = hd.tmute0; this.tmutef = hd.tmutef; this.trid = hd.trid; this.trnof = hd.trnof; this.trseql = hd.trseql; this.trseqr = hd.trseqr; this.trwt = hd.trwt; this.tug = hd.tug; this.tus = hd.tus; this.use = hd.use; this.vsbweath = hd.vsbweath; this.vsumno = hd.vsumno; this.vweath = hd.vweath; this.year = hd.year; /* for (int i=0; i<40; i++) this.unas[i] = hd.unas[i]; */ this.samp_rate = hd.samp_rate; this.data_form = hd.data_form; this.m_secs = hd.m_secs; this.trigyear = hd.trigyear; this.trigday = hd.trigday; this.trighour = hd.trighour; this.trigminute = hd.trigminute; this.trigsecond = hd.trigsecond; this.trigmills = hd.trigmills; this.scale_fac = hd.scale_fac; this.inst_no = hd.inst_no; this.not_to_be_used = hd.not_to_be_used; this.num_samps = hd.num_samps; this.max = hd.max; this.min = hd.min; } public void read(RandomAccessFile dis) throws IOException, EOFException { this.trseql = dis.readInt(); if (this.trseql < 0) throw new EOFException(); this.trseqr = dis.readInt(); this.frecno = dis.readInt(); this.trnof = dis.readInt(); this.sp = dis.readInt(); this.cdpensno = dis.readInt(); this.enstrno = dis.readInt(); this.trid = dis.readShort(); this.vsumno = dis.readShort(); this.hsumno = dis.readShort(); this.use = dis.readShort(); this.offset = dis.readInt(); this.gz = dis.readInt(); this.szsurf = dis.readInt(); this.sdepth = dis.readInt(); this.gdatz = dis.readInt(); this.sdatz = dis.readInt(); this.swatdep = dis.readInt(); this.gwatdep = dis.readInt(); this.lscaler = dis.readShort(); this.coscaler = dis.readShort(); this.sx = dis.readInt(); this.sy = dis.readInt(); this.gx = dis.readInt(); this.gy = dis.readInt(); this.counit = dis.readShort(); this.vweath = dis.readShort(); this.vsbweath = dis.readShort(); this.tus = dis.readShort(); this.tug = dis.readShort(); this.dts = dis.readShort(); this.dtg = dis.readShort(); this.dttotal = dis.readShort(); this.tlA = dis.readShort(); this.tlB = dis.readShort(); this.delay = dis.readShort(); this.tmute0 = dis.readShort(); this.tmutef = dis.readShort(); this.nt = dis.readShort(); this.dt = dis.readShort(); this.gaintype = dis.readShort(); this.kgain = dis.readShort(); this.gain0 = dis.readShort(); this.correl = dis.readShort(); this.swf0 = dis.readShort(); this.swff = dis.readShort(); this.swt = dis.readShort(); this.swtype = dis.readShort(); this.swtrtpt0 = dis.readShort(); this.swtrtptf = dis.readShort(); this.swtaptype = dis.readShort(); this.alff = dis.readShort(); this.alfsl = dis.readShort(); this.nchff = dis.readShort(); this.nchfsl = dis.readShort(); this.lcf = dis.readShort(); this.hcf = dis.readShort(); this.lcsl = dis.readShort(); this.hcsl = dis.readShort(); this.year = dis.readShort(); this.jday = dis.readShort(); this.hour = dis.readShort(); this.minute = dis.readShort(); this.second = dis.readShort(); this.tbasis = dis.readShort(); this.trwt = dis.readShort(); this.rsw1gno = dis.readShort(); this.frtr1gno = dis.readShort(); this.frtrfgno = dis.readShort(); this.gapsize = dis.readShort(); this.overtrav = dis.readShort(); this.fdt = dis.readInt(); this.fdts = dis.readInt(); this.fdtg = dis.readInt(); this.fdtd = dis.readInt(); this.fdtmo = dis.readInt(); /* for (int i=0; i<40; i++) this.unas[i] = dis.readByte(); */ this.samp_rate = dis.readInt(); this.data_form = dis.readShort(); this.m_secs = dis.readShort(); this.trigyear = dis.readShort(); this.trigday = dis.readShort(); this.trighour = dis.readShort(); this.trigminute = dis.readShort(); this.trigsecond = dis.readShort(); this.trigmills = dis.readShort(); this.scale_fac = dis.readFloat(); /* this.scale_fac == 0F signifies no valid scale factor */ if (Float.isNaN(this.scale_fac)) this.scale_fac = 0F; else if (this.scale_fac > 1e38f || this.scale_fac < -1e38f) this.scale_fac = 0F; this.inst_no = dis.readShort(); this.not_to_be_used = dis.readShort(); this.num_samps = dis.readInt(); this.max = dis.readInt(); this.min = dis.readInt(); } public void write(DataOutputStream dos) throws IOException { dos.writeInt(trseql); dos.writeInt(trseqr); dos.writeInt(frecno); dos.writeInt(trnof); dos.writeInt(sp); dos.writeInt(cdpensno); dos.writeInt(enstrno); dos.writeShort(trid); dos.writeShort(vsumno); dos.writeShort(hsumno); dos.writeShort(use); dos.writeInt(offset); dos.writeInt(gz); dos.writeInt(szsurf); dos.writeInt(sdepth); dos.writeInt(gdatz); dos.writeInt(sdatz); dos.writeInt(swatdep); dos.writeInt(gwatdep); dos.writeShort(lscaler); dos.writeShort(coscaler); dos.writeInt(sx); dos.writeInt(sy); dos.writeInt(gx); dos.writeInt(gy); dos.writeShort(counit); dos.writeShort(vweath); dos.writeShort(vsbweath); dos.writeShort(tus); dos.writeShort(tug); dos.writeShort(dts); dos.writeShort(dtg); dos.writeShort(dttotal); dos.writeShort(tlA); dos.writeShort(tlB); dos.writeShort(delay); dos.writeShort(tmute0); dos.writeShort(tmutef); dos.writeShort(nt); dos.writeShort(dt); dos.writeShort(gaintype); dos.writeShort(kgain); dos.writeShort(gain0); dos.writeShort(correl); dos.writeShort(swf0); dos.writeShort(swff); dos.writeShort(swt); dos.writeShort(swtype); dos.writeShort(swtrtpt0); dos.writeShort(swtrtptf); dos.writeShort(swtaptype); dos.writeShort(alff); dos.writeShort(alfsl); dos.writeShort(nchff); dos.writeShort(nchfsl); dos.writeShort(lcf); dos.writeShort(hcf); dos.writeShort(lcsl); dos.writeShort(hcsl); dos.writeShort(year); dos.writeShort(jday); dos.writeShort(hour); dos.writeShort(minute); dos.writeShort(second); dos.writeShort(tbasis); dos.writeShort(trwt); dos.writeShort(rsw1gno); dos.writeShort(frtr1gno); dos.writeShort(frtrfgno); dos.writeShort(gapsize); dos.writeShort(overtrav); dos.writeInt(fdt); dos.writeInt(fdts); dos.writeInt(fdtg); dos.writeInt(fdtd); dos.writeInt(fdtmo); /* for (int i=0; i<40; i++) dos.writeByte(this.unas[i]); */ dos.writeInt(samp_rate); dos.writeShort(data_form); dos.writeShort(m_secs); dos.writeShort(trigyear); dos.writeShort(trigday); dos.writeShort(trighour); dos.writeShort(trigminute); dos.writeShort(trigsecond); dos.writeShort(trigmills); if (scale_fac == 0F) dos.writeFloat(1F); else dos.writeFloat(scale_fac); dos.writeShort(inst_no); dos.writeShort(not_to_be_used); dos.writeInt(num_samps); dos.writeInt(max); dos.writeInt(min); } public String toString() { return "frecno=" + frecno + " trnof=" + trnof + " sp=" + sp + " cdpensno=" + cdpensno + "\noffset=" + offset + " gz=" + gz + " szsurf=" + szsurf + " sdepth=" + sdepth + " gdatz=" + gdatz + " sdatz=" + sdatz + "\nlscaler=" + lscaler + " coscaler=" + coscaler + " sx=" + sx + " sy=" + sy + " gx=" + gx + " gy=" + gy + " counit=" + counit + "\ndelay=" + delay + " nt=" + nt + " dt=" + dt + " rsw1gno=" + rsw1gno + " frtr1gno=" + frtr1gno /* + " unas=" + unas; */ + " samp_rate=" + samp_rate + " data_form=" + data_form + " m_secs=" + m_secs + " trigyear=" + trigyear + " trigday=" + trigday + " trighour=" + trighour + " trigminute=" + trigminute + " trigsecond=" + trigsecond + " trigmills=" + trigmills + " scale_fac=" + scale_fac + " inst_no=" + inst_no + " not_to_be_used=" + not_to_be_used + " num_samps=" + num_samps + " max=" + max + " min=" + min; } /* float_to_ibm(long from[], long to[], long n) from the Colorado School of Mines, 1996 */ /* adapted for Java by J. Louie 9/11/00 */ public static int floatToIntBitsIBM(float from) { int fconv, fmant, t; fconv = Float.floatToIntBits(from); if (fconv != 0) { fmant = (0x007fffff & fconv) | 0x00800000; t = (int) ((0x7f800000 & fconv) >> 23) - 126; while ((t & 0x3) != 0) { ++t; fmant >>= 1; } fconv = (0x80000000 & fconv) | (((t>>2) + 64) << 24) | fmant; } return fconv; } /*************************************************************************** ibm2ieee: routine to convert from short (32 bit) ibm-standard floating point numbers (see Barry et al., Geophysics, 40, 2, 344-352, 1975) to ieee- standard floating point numbers. This routine was adapted from "ibmiee.c" (written by M. Weidersphan, U.T., Austin) to convert numbers "in place". *****************************************************************************/ /* adapted for Java by J. Louie 7/23/99 */ public static float intBitsIBMToFloat(int fpn) { int exponent, mantissa, sign; if ((fpn & MSK_MANT_IBM) == 0) return 0F; else { mantissa = (fpn & MSK_MANT_IBM); exponent = ((((fpn & MSK_EXP_IBM) >> 24) - 64) << 2 ); /*exponent = ((((fpn & MSK_EXP_IBM) >> 24) - 64 - 23));*/ sign = (fpn & MSK_SIGN_IBM); /* if (sign != 0) return -((float)(Math.pow(mantissa, exponent))); else return ((float)(Math.pow(mantissa, exponent))); */ while ((mantissa & MSK_NORM_IEEE) == 0) { mantissa <<= 1; /* normalize */ exponent-- ; } mantissa = mantissa & 0x7fffff; /* shift understood one out */ exponent += 126; if (( exponent < 0 ) || (exponent > 255)) /* IBM floating point exponent out of range */ exponent = 0; exponent <<= 23; return Float.intBitsToFloat(sign | exponent | mantissa); } } }