📄 segywrite.c
字号:
} } else { fwrite((char *) &tapebh, 1, BNYBYTES, tapefp); if (ferror(tapefp)) { if (verbose) warn("tape write error on binary header"); if (++errcount > errmax) err("exceeded maximum io errors"); clearerr(tapefp); } else { /* Reset counter on successful tape IO */ errcount = 0; } }#endif /* end if SUXDR */ /* Copy traces from stdin to tape */#ifdef SUXDR /* begin SUXDR */ trbuf = (char *) alloc1(nsegy, sizeof(char)); xdrmem_create(&trhd_xdr,trbuf,(unsigned int) nsegy,XDR_ENCODE); trstart = xdr_getpos(&trhd_xdr);#endif /* end if SUXDR */ itr = 0; do { /* Set/check trace header words */ tr.tracr = ++itr; if (tr.ns != ns) err("conflict: tr.ns = %d, bh.ns = %d: trace %d", tr.ns, ns, itr); /* Convert and write desired traces */ if (itr >= trmin) {#ifdef SUXDR /* begin SUXDR */ /* convert trace header to SEGY standard */ if(FALSE == xdr_setpos(&trhd_xdr,trstart)) err("%s: trouble \"seeking\" start of trace", __FILE__); xdrhdrsub(&trhd_xdr,&tr); /* Convert internal floats to IBM floats */ if (conv) {#if defined(CRAY)#if defined(_CRAYMPP) float_to_ibm((fourbyte *) (&(tr.data[0])), (fourbyte *) (&(tr.data[0])), ns, endian);/* Stew's Fortran routine... fns = ns; IBMFLT(tr.data,tr.data,&fns,&imone);*/#else /* !_CRAYMPP */ USSCTI(tr.data,tr.data,&ione,&ns,&ier);#endif /* _CRAYMPP */#else /* !CRAY */ float_to_ibm((fourbyte *) (&(tr.data[0])), (fourbyte *) (&(tr.data[0])), ns, endian);#endif /* !CRAY */ memcpy(trbuf+SEGY_HDRBYTES,(char *) tr.data, ns*4*sizeof(char)); } else { xdr_vector(&trhd_xdr,(char *) tr.data, ns, sizeof(float), (xdrproc_t) xdr_float); } /* Write the trace to tape */ if (buff) { if (nsegy != write(tapefd, trbuf, nsegy)){ if (verbose) warn("tape write error on trace %d", itr); if (++errcount > errmax) err("exceeded maximum io errors"); } else { /* Reset counter on successful tape IO */ errcount = 0; } } else { fwrite(trbuf,sizeof(char),nsegy,tapefp); if (ferror(tapefp)) { if (verbose) warn("tape write error on trace %d", itr); if (++errcount > errmax) err("exceeded maximum io errors"); clearerr(tapefp); } else { /* Reset counter on successful tape IO */ errcount = 0; } }#else /* not SUXDR */ /* Convert internal floats to IBM floats */ if (conv) float_to_ibm((int *) tr.data, (int *) tr.data, ns, endian); /* handle no ibm conversion for little endian case */ if (conv==0 && endian==0) for (i = 0; i < ns ; ++i) swap_float_4(&tr.data[i]); /* if little endian, swap bytes in header */ if (endian==0) for (i = 0; i < SEGY_NKEYS; ++i) swaphval(&tr,i); /* Convert from ints/shorts to bytes */ segy_to_tapesegy(&tr, &tapetr, nsegy); /* Write the trace to tape */ if (buff) { if (nsegy != write(tapefd, (char *) &tapetr, nsegy)){ if (verbose) warn("tape write error on trace %d", itr); if (++errcount > errmax) err("exceeded maximum io errors"); } else { /* Reset counter on successful tape IO */ errcount = 0; } } else { fwrite((char *)&tapetr,1,nsegy,tapefp); if (ferror(tapefp)) { if (verbose) warn("tape write error on trace %d", itr); if (++errcount > errmax) err("exceeded maximum io errors"); clearerr(tapefp); } else { /* Reset counter on successful tape IO */ errcount = 0; } }#endif /* end if SUXDR */ /* Echo under verbose option */ if (verbose && itr % vblock == 0) warn(" %d traces written to tape", itr); } } while (gettr(&tr) && itr < trmax); /* Clean up */ (buff) ? eclose(tapefd) : efclose(tapefp); if (verbose) warn("tape closed successfully");#ifdef SUXDR /* begin SUXDR */ xdr_destroy(&trhd_xdr); xdr_destroy(&bhed_xdr); xdr_destroy(&bhbuf_xdr);#endif /* end if SUXDR */ efclose(binaryfp); if (verbose) warn("binary file closed successfully");#ifndef SUXDR /* begin not SUXDR */ epclose(pipefp);#endif /* end if not SUXDR */ return(CWP_Exit());}#ifdef SUXDR /* begin SUXDR *//* Assumes fourbyte == 4 byte integer */static void float_to_ibm(fourbyte *from, fourbyte *to, int n, int endian)/********************************************************************** float_to_ibm - convert between 32 bit IBM and IEEE floating numbers*********************************************************************** Input:from input vectorn number of floats in vectorsendian =0 for little endian machine, =1 for big endian machinesOutput:to output vector, can be same as input vector*********************************************************************** Notes:Up to 3 bits lost on IEEE -> IBMIBM -> IEEE may overflow or underflow, taken care of by substituting large number or zeroOnly integer shifting and masking are used.*********************************************************************** Credits: CWP: Brian Sumner***********************************************************************/{ register fourbyte fconv, fmant, t; register int i; for (i=0;i<n;++i) { fconv = from[i]; if (fconv) { fmant = (0x007fffff & fconv) | 0x00800000; t = (fourbyte) ((0x7f800000 & fconv) >> 23) - 126; while (t & 0x3) { ++t; fmant >>= 1; } fconv = (0x80000000 & fconv) | (((t>>2) + 64) << 24) | fmant; } if(endian==0) fconv = (fconv<<24) | ((fconv>>24)&0xff) | ((fconv&0xff00)<<8) | ((fconv&0xff0000)>>8); to[i] = fconv; } return;}#else /* not SUXDR */#ifdef _HPUX_SOURCEvoid float_to_ibm(int from[], int to[], int n, int endian){ register int fconv, fmant, i, t, dummy; dummy = endian; for (i=0;i<n;++i) { fconv = from[i]; if (fconv) { fmant = (0x007fffff & fconv) | 0x00800000; t = (int) ((0x7f800000 & fconv) >> 23) - 126; while (t & 0x3) { ++t; fmant >>= 1; } fconv = (0x80000000 & fconv) | (((t>>2) + 64) << 24) | fmant; } to[i] = fconv; } return;}#else/* Assumes sizeof(int) == 4 */static void float_to_ibm(int from[], int to[], int n, int endian)/********************************************************************** float_to_ibm - convert between 32 bit IBM and IEEE floating numbers*********************************************************************** Input:from input vectorn number of floats in vectorsendian =0 for little endian machine, =1 for big endian machinesOutput:to output vector, can be same as input vector*********************************************************************** Notes:Up to 3 bits lost on IEEE -> IBMIBM -> IEEE may overflow or underflow, taken care of by substituting large number or zeroOnly integer shifting and masking are used.*********************************************************************** Credits: CWP: Brian Sumner***********************************************************************/{ register int fconv, fmant, i, t; for (i=0;i<n;++i) { fconv = from[i]; if (fconv) { fmant = (0x007fffff & fconv) | 0x00800000; t = (int) ((0x7f800000 & fconv) >> 23) - 126; while (t & 0x3) { ++t; fmant >>= 1; } fconv = (0x80000000 & fconv) | (((t>>2) + 64) << 24) | fmant; } if(endian==0) fconv = (fconv<<24) | ((fconv>>24)&0xff) | ((fconv&0xff00)<<8) | ((fconv&0xff0000)>>8); to[i] = fconv; } return;}#endif static void bhed_to_tapebhed(const bhed *bhptr, tapebhed *tapebhptr)/***************************************************************************bhed_tape_bhed -- converts the binary tape header in the machine's shortand int types to, respectively, the seg-y standard 2 byte and 4 byte integertypes.****************************************************************************Input:bhptr pointer to binary header vectorOutput:tapebhptr pointer to tape binary header vector****************************************************************************Notes:The present implementation assumes that these types are actually the "right"size (respectively 2 and 4 bytes), so this routine is only a placeholder forthe conversions that would be needed on a machine not using this convention.****************************************************************************Author: CWP: Jack K. Cohen August 1994***************************************************************************/{ register int i; Value val; /* convert the binary header field by field */ for (i = 0; i < BHED_NKEYS; ++i) { getbhval(bhptr, i, &val); puttapebhval(tapebhptr, i, &val); }}staticvoid segy_to_tapesegy(const segy *trptr, tapesegy *tapetrptr, size_t nsegy)/***************************************************************************tapesegy_to_segy -- converts the integer header fields from, respectively, the machine's short and int types to the seg-y standard 2 byte and 4 byte types.****************************************************************************Input:trptr pointer to SU SEG-Y data vector nsegy whole size of a SEG-Y trace in bytesOutput:tapetrptr pointer to tape SEG-Y data vector****************************************************************************Notes:Also copies the float data byte by byte. The present implementation assumesthat the integer types are actually the "right" size (respectively 2 and4 bytes), so this routine is only a placeholder for the conversions thatwould be needed on a machine not using this convention. The float datais preserved as four byte fields and is later converted to internal floatsby float_to_ibm (which, in turn, makes additonal assumptions)****************************************************************************Author: CWP: Jack K. Cohen August 1994***************************************************************************/{ register int i; Value val; /* convert trace header, field by field */ for (i = 0; i < SEGY_NKEYS; ++i) { gethval(trptr, i, &val); puttapehval(tapetrptr, i, &val); } /* copy optional portion */ memcpy(tapetrptr->unass, (char *)&(trptr->otrav)+2, 60); /* copy data portion */ memcpy(tapetrptr->data, trptr->data, 4*SU_NFLTS);} #endif /* end if SUXDR */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -