esig_edr.c

来自「speech signal process tools」· C语言 代码 · 共 2,690 行 · 第 1/4 页

C
2,690
字号
		}#else  /* 32-bit unsigned longs */		{		    if (hi != 0)		    {			data[n] = ULONG_MAX;			/* CLIPPING */		    }		    else			data[n] = lo;		}#endif	    }	    return n;	}	break;    default:	return 0;    }}/* Read items of type SHORT */static intEdrReadShort(short  *data,	     long   length,	     FILE   *file){    long	    n;		/* number of items read */    unsigned int    item;	/* one input data item */    int		    ch;		/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	item = ch;	if ((ch = getc(file)) == EOF)	    break;	item = (item << 8) | ch;	data[n] =	    (item & 0x8000)		? (-1 - (int) (item ^ 0xffff))		    : item;    }    return n;}/* Read items of type USHORT */static intEdrReadUshort(Ushort *data,	      long length,	      FILE *file){    long	    n;		/* number of items read */    unsigned int    item;	/* one input data item */    int		    ch;		/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	item = ch;	if ((ch = getc(file)) == EOF)	    break;	item = (item << 8) | ch;	data[n] = item;    }    return n;}/* Read items of type SCHAR */static intEdrReadSchar(Schar  *data,	     long   length,	     FILE   *file){    long    n;			/* number of items read */    int	    ch;			/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	data[n] = (ch & 0x80) ? ch - 0x100 : ch;    }    return n;}/* Read items of type UCHAR */static intEdrReadUchar(Uchar  *data,	     long   length,	     FILE   *file){    long	    n;		/* number of items read */    int		    ch;		/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	data[n] = ch;    }    return n;}/* Read items of type BOOL */static intEdrReadBool(Bool    *data,	    long    length,	    FILE    *file){    long	    n;		/* number of items read */    int		    ch;		/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	data[n] = (ch != 0);    }    return n;}/* Read items of type DOUBLE_COMPLEX */static intEdrReadDoubleComplex(DoubleComplex  *data,		     long	    length,		     FILE	    *file){    long	    n;		/* number of items read */    double	    x[2];	/* real and imaginary parts */    for (n = 0; n < length; n++)    {	if (EdrReadDouble(x, 2, file) != 2)	    break;	data[n].real = x[0];	data[n].imag = x[1];    }    return n;}/* Read items of type FLOAT_COMPLEX */static intEdrReadFloatComplex(FloatComplex    *data,		    long	    length,		    FILE	    *file){    long	    n;		/* number of items read */    float	    x[2];	/* real and imaginary parts */    for (n = 0; n < length; n++)    {	if (EdrReadFloat(x, 2, file) != 2)	    break;	data[n].real = x[0];	data[n].imag = x[1];    }    return n;}/* Read items of type LONG_COMPLEX */static intEdrReadLongComplex(LongComplex  *data,		   long	    length,		   FILE	    *file,		   int	    longlong){    long	    n;		/* number of items read */    long	    x[2];	/* real and imaginary parts */    for (n = 0; n < length; n++)    {	if (EdrReadLong(x, 2, file, longlong) != 2)	    break;	data[n].real = x[0];	data[n].imag = x[1];    }    return n;}/* Read items of type SHORT_COMPLEX */static intEdrReadShortComplex(ShortComplex    *data,		    long	    length,		    FILE	    *file){    long	    n;		/* number of items read */    short	    x[2];	/* real and imaginary parts */    for (n = 0; n < length; n++)    {	if (EdrReadShort(x, 2, file) != 2)	    break;	data[n].real = x[0];	data[n].imag = x[1];    }    return n;}/* Read items of type SCHAR_COMPLEX */static intEdrReadScharComplex(ScharComplex    *data,		    long	    length,		    FILE	    *file){    long	    n;		/* number of items read */    Schar	    x[2];	/* real and imaginary parts */    for (n = 0; n < length; n++)    {	if (EdrReadSchar(x, 2, file) != 2)	    break;	data[n].real = x[0];	data[n].imag = x[1];    }    return n;}/* Read items of type CHAR */static intEdrReadChar(char *data,	    long length,	    FILE *file){    long    n;			/* number of items read */    int	    ch;			/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	data[n] = ch;    }    return n;}/* Read items of type WCHAR */static intEdrReadWchar(Wchar	*data,	     long	length,	     FILE	*file){    long	    n;		/* number of items read */    unsigned int    item;	/* one input data item */    int		    ch;		/* input character */    for (n = 0; n < length; n++)    {	if ((ch = getc(file)) == EOF)	    break;	item = ch;	if ((ch = getc(file)) == EOF)	    break;	item = (item << 8) | ch;	data[n] = item;    }    return n;}/* * *** FUNCTIONS FOR OUTPUT *//* * Write "data" member of field to file in EDR format. * Return TRUE on success, FALSE on failure. */static intWriteEdrData(FieldSpec	*field,	     FILE	*file,	     int	longlong){    long    length;		/* number of elements */    if (file  == NULL || field == NULL || field->type == NO_TYPE)	return FALSE;    length = FieldLength(field);    if (length != 0 && field->data == NULL)	return FALSE;    if (EdrWrite(field->data,		 field->type, length, file, longlong) != length)	return FALSE;    return TRUE;}/* * Write field specification to file in EDR format. * Return TRUE on success, FALSE on failure. */static intWriteEdrFieldSpec(FieldSpec *field,		  FILE	    *file,		  int	    longlong){    int     rank;		/* number of dimensions */    int     i;			/* loop index */    long    num_ax_names;	/* number of axis names */    if (file == NULL || field == NULL)	return FALSE;    if (!WriteEdrString(field->name, file, longlong))	return FALSE;    if (EdrWriteShort(&field->type, 1, file) != 1)	return FALSE;    if (EdrWriteShort(&field->rank, 1, file) != 1)	return FALSE;    rank = field->rank;    if (rank != 0 && field->dim == NULL)	return FALSE;		/* Inconsistent rank and dimensions. */    if (EdrWriteLong(field->dim, rank, file, longlong) != rank)	return FALSE;    if (!WriteEdrString(field->units, file, longlong))	return FALSE;    if (EdrWriteDouble(&field->scale, 1, file) != 1)	return FALSE;    if (EdrWriteDouble(&field->offset, 1, file) != 1)	return FALSE;    num_ax_names = (field->axis_names == NULL) ? 0 : rank;    if (EdrWriteLong(&num_ax_names, 1, file, longlong) != 1)	return FALSE;    for (i = 0; i < num_ax_names; i++)	if (!WriteEdrString(field->axis_names[i], file, longlong))	    return FALSE;    if (EdrWriteShort(&field->occurrence, 1, file) != 1)	return FALSE;    if (field->type != NO_TYPE	&& field->occurrence != REQUIRED && field->occurrence != OPTIONAL)    {	if (!WriteEdrData(field, file, longlong))	    return FALSE;    }    if (!WriteEdrFieldList(field->subfields, file, longlong))	return FALSE;    return TRUE;}/* * Write a string to a file in portable binary format:  the string length * in EDR1 or EDR2 LONG format, followed by the characters of the string. * Return TRUE on success and FALSE in case of failure. */static intWriteEdrString(char	*string,	       FILE	*file,	       int	longlong){    long    length;    long    i;    if (file == NULL)	return FALSE;    if (string == NULL)	string = "";    length = strlen(string);    if (EdrWriteLong(&length, 1, file, longlong) != 1)	return FALSE;		/* Couldn't write length. */    for (i = 0; i < length && putc(string[i], file) != EOF; i++)    { }    return (i == length);}/* * Write items of data to a file in EDR1 or EDR2 portable binary format * from the block of storage indicated by the pointer "data". * The number of items is given by "length", and their data type * is indicated by the integer code "type". * Return the number of successfully written items.  (A value other * than "length" indicates an error). */static intEdrWrite(void	*data,	 int	type,	 long	length,	 FILE	*file,	 int	longlong){    if (file == NULL || data == NULL || length <= 0)	return 0;    switch (type)    {    case ARRAY:	return EdrWriteArray((Array *) data, length, file, longlong);    case DOUBLE:	return EdrWriteDouble((double *) data, length, file);    case FLOAT:	return EdrWriteFloat((float *) data, length, file);    case LONG:	return EdrWriteLong((long *) data, length, file, longlong);    case ULONG:	return EdrWriteUlong((Ulong *) data, length, file, longlong);    case SHORT:	return EdrWriteShort((short *) data, length, file);    case USHORT:	return EdrWriteUshort((Ushort *) data, length, file);    case SCHAR:	return EdrWriteSchar((Schar *) data, length, file);    case UCHAR:	return EdrWriteUchar((Uchar *) data, length, file);    case BOOL:	return EdrWriteBool((Bool *) data, length, file);    case DOUBLE_COMPLEX:	return EdrWriteDoubleComplex((DoubleComplex *) data, length, file);    case FLOAT_COMPLEX:	return EdrWriteFloatComplex((FloatComplex *) data, length, file);    case LONG_COMPLEX:	return EdrWriteLongComplex((LongComplex *) data,				   length, file, longlong);    case SHORT_COMPLEX:	return EdrWriteShortComplex((ShortComplex *) data, length, file);    case SCHAR_COMPLEX:	return EdrWriteScharComplex((ScharComplex *) data, length, file);    case CHAR:	return EdrWriteChar((char *) data, length, file);    case WCHAR:	return EdrWriteWchar((Wchar *) data, length, file);    default:    /* Invalid code or NO_TYPE. */	return 0;    }}/* * Write to "file" the EDR1 or EDR2 representation of one item of type * ARRAY from the location indicated by "array". * Return TRUE for success, FALSE for failure. */static intWriteEdrArray(Array *array,	      FILE  *file,	      int   longlong){    short   type;    short   rank;    long    *dim;    void    *data;    long    length;    if (file == NULL || array == NULL)	return FALSE;    type = array->type;    rank = array->rank;    dim = array->dim;    data = array->data;    if (EdrWriteShort(&type, 1, file) != 1)	return FALSE;    if (EdrWriteShort(&rank, 1, file) != 1)	return FALSE;    if (rank > 0)    {	if (dim == NULL)	    return FALSE;	if (EdrWriteLong(dim, rank, file, longlong) != rank)	    return FALSE;    }    length = LongProd(rank, dim);    if (length > 0)    {	if (data == NULL)	    return FALSE;	if (EdrWrite(data, type, length, file, longlong) != length)	    return FALSE;    }    return TRUE;}/* * Each of the following functions with names of the form * *      EdrWrite<type> * * takes three arguments: *	<type>	*data, *	long	length, *	FILE	*file, * and in some cases a fourth: *	int	longlong * The function writes "length" items of data of the indicated data type * in EDR portable binary format to the stream "file" from the block of * storage indicated by "data".  The fourth argument, "longlong", is * present when the EDR1 and EDR2 representations of the data type differ; * a value of 1 indicates EDR1, and 2 indicates EDR2.  The int return * value is the number of items successfully written, which will be less * than "length" in case of error. *//* Write items of type ARRAY */static intEdrWriteArray(Array	*data,	      long	length,	      FILE	*file,	      int	longlong){    long	n;    for (n = 0;	 n < length && WriteEdrArray(&data[n], file, longlong);	 n++)    { }    return n;}/* Write items of type DOUBLE */static intEdrWriteDouble(double	*data,	       long	length,	       FILE	*file){    long	    n;		/* number of items written */    double	    item;	/* one data item for output */    int		    sn;		/* set sign bit? */    int		    ex;		/* exponent */    unsigned long   hi;		/* high-order fraction bits				   (28 plus one hidden) */    unsigned long   lo;		/* 24 low-order fraction bits */    double	    hix, lox;	/* hi and lo as double */    for (n = 0; n < length; n++)    {	item = data[n];	if (!(item <= DBL_MAX))	/* Inf or NaN */	    /* Don't change to if (item > DBL_MAX)! */	{	    if (item > DBL_MAX)	/* Inf */	    {		ex = 0x7ff;		hi = 0x0000000;		lo = 0x000000;	    }	    else		/* NaN */	    {		ex = 0x7ff;		hi = 0xfffffff;		lo = 0xffffff;	    }	}	else if (item < -DBL_MAX)	/* -Inf */	{	    ex = 0xfff;	    hi = 0x0000000;	    lo = 0x000000;	}	else	{	    sn = (item < 0.0);	    item = frexp((sn) ? -item : item, &ex);	    if (item == 0)		ex = -1021;	    else if (ex < -1021)	    {		item = ldexp(item, 29 - (-1021 - ex));		ex = -1021;	    }	    else		item = ldexp(item, 29);	    lox = modf(item, &hix);	    lo = 0.5 + ldexp(lox, 24);	    if (lo >= 0x1000000) /* 2^24 */	    {		lo -= 0x1000000; /* 2^24 */		hi = 1 + (unsigned long) hix;	    }	    else		hi = (unsigned long) hix;	    if (hi >= 0x20000000) /* 2^29 */	    {		hi = 0x10000000; /* 2^28 */		lo = 0;

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?