2 ** Copyright (C) 1999-2011 Erik de Castro Lopo <erikd@mega-nerd.com>
4 ** This program is free software; you can redistribute it and/or modify
5 ** it under the terms of the GNU Lesser General Public License as published by
6 ** the Free Software Foundation; either version 2.1 of the License, or
7 ** (at your option) any later version.
9 ** This program is distributed in the hope that it will be useful,
10 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
11 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 ** GNU Lesser General Public License for more details.
14 ** You should have received a copy of the GNU Lesser General Public License
15 ** along with this program; if not, write to the Free Software
16 ** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
31 #if CPU_IS_LITTLE_ENDIAN
32 #define FLOAT32_READ float32_le_read
33 #define FLOAT32_WRITE float32_le_write
34 #elif CPU_IS_BIG_ENDIAN
35 #define FLOAT32_READ float32_be_read
36 #define FLOAT32_WRITE float32_be_write
39 /*--------------------------------------------------------------------------------------------
40 ** Processor floating point capabilities. float32_get_capability () returns one of the
41 ** latter four values.
45 { FLOAT_UNKNOWN
= 0x00,
46 FLOAT_CAN_RW_LE
= 0x12,
47 FLOAT_CAN_RW_BE
= 0x23,
48 FLOAT_BROKEN_LE
= 0x34,
49 FLOAT_BROKEN_BE
= 0x45
52 /*--------------------------------------------------------------------------------------------
53 ** Prototypes for private functions.
56 static sf_count_t
host_read_f2s (SF_PRIVATE
*psf
, short *ptr
, sf_count_t len
) ;
57 static sf_count_t
host_read_f2i (SF_PRIVATE
*psf
, int *ptr
, sf_count_t len
) ;
58 static sf_count_t
host_read_f (SF_PRIVATE
*psf
, float *ptr
, sf_count_t len
) ;
59 static sf_count_t
host_read_f2d (SF_PRIVATE
*psf
, double *ptr
, sf_count_t len
) ;
61 static sf_count_t
host_write_s2f (SF_PRIVATE
*psf
, const short *ptr
, sf_count_t len
) ;
62 static sf_count_t
host_write_i2f (SF_PRIVATE
*psf
, const int *ptr
, sf_count_t len
) ;
63 static sf_count_t
host_write_f (SF_PRIVATE
*psf
, const float *ptr
, sf_count_t len
) ;
64 static sf_count_t
host_write_d2f (SF_PRIVATE
*psf
, const double *ptr
, sf_count_t len
) ;
66 static void float32_peak_update (SF_PRIVATE
*psf
, const float *buffer
, int count
, sf_count_t indx
) ;
68 static sf_count_t
replace_read_f2s (SF_PRIVATE
*psf
, short *ptr
, sf_count_t len
) ;
69 static sf_count_t
replace_read_f2i (SF_PRIVATE
*psf
, int *ptr
, sf_count_t len
) ;
70 static sf_count_t
replace_read_f (SF_PRIVATE
*psf
, float *ptr
, sf_count_t len
) ;
71 static sf_count_t
replace_read_f2d (SF_PRIVATE
*psf
, double *ptr
, sf_count_t len
) ;
73 static sf_count_t
replace_write_s2f (SF_PRIVATE
*psf
, const short *ptr
, sf_count_t len
) ;
74 static sf_count_t
replace_write_i2f (SF_PRIVATE
*psf
, const int *ptr
, sf_count_t len
) ;
75 static sf_count_t
replace_write_f (SF_PRIVATE
*psf
, const float *ptr
, sf_count_t len
) ;
76 static sf_count_t
replace_write_d2f (SF_PRIVATE
*psf
, const double *ptr
, sf_count_t len
) ;
78 static void bf2f_array (float *buffer
, int count
) ;
79 static void f2bf_array (float *buffer
, int count
) ;
81 static int float32_get_capability (SF_PRIVATE
*psf
) ;
83 /*--------------------------------------------------------------------------------------------
84 ** Exported functions.
88 float32_init (SF_PRIVATE
*psf
)
89 { static int float_caps
;
91 float_caps
= float32_get_capability (psf
) ;
93 psf
->blockwidth
= sizeof (float) * psf
->sf
.channels
;
95 if (psf
->file
.mode
== SFM_READ
|| psf
->file
.mode
== SFM_RDWR
)
96 { switch (psf
->endian
+ float_caps
)
97 { case (SF_ENDIAN_BIG
+ FLOAT_CAN_RW_BE
) :
98 psf
->data_endswap
= SF_FALSE
;
99 psf
->read_short
= host_read_f2s
;
100 psf
->read_int
= host_read_f2i
;
101 psf
->read_float
= host_read_f
;
102 psf
->read_double
= host_read_f2d
;
105 case (SF_ENDIAN_LITTLE
+ FLOAT_CAN_RW_LE
) :
106 psf
->data_endswap
= SF_FALSE
;
107 psf
->read_short
= host_read_f2s
;
108 psf
->read_int
= host_read_f2i
;
109 psf
->read_float
= host_read_f
;
110 psf
->read_double
= host_read_f2d
;
113 case (SF_ENDIAN_BIG
+ FLOAT_CAN_RW_LE
) :
114 psf
->data_endswap
= SF_TRUE
;
115 psf
->read_short
= host_read_f2s
;
116 psf
->read_int
= host_read_f2i
;
117 psf
->read_float
= host_read_f
;
118 psf
->read_double
= host_read_f2d
;
121 case (SF_ENDIAN_LITTLE
+ FLOAT_CAN_RW_BE
) :
122 psf
->data_endswap
= SF_TRUE
;
123 psf
->read_short
= host_read_f2s
;
124 psf
->read_int
= host_read_f2i
;
125 psf
->read_float
= host_read_f
;
126 psf
->read_double
= host_read_f2d
;
129 /* When the CPU is not IEEE compatible. */
130 case (SF_ENDIAN_BIG
+ FLOAT_BROKEN_LE
) :
131 psf
->data_endswap
= SF_TRUE
;
132 psf
->read_short
= replace_read_f2s
;
133 psf
->read_int
= replace_read_f2i
;
134 psf
->read_float
= replace_read_f
;
135 psf
->read_double
= replace_read_f2d
;
138 case (SF_ENDIAN_LITTLE
+ FLOAT_BROKEN_LE
) :
139 psf
->data_endswap
= SF_FALSE
;
140 psf
->read_short
= replace_read_f2s
;
141 psf
->read_int
= replace_read_f2i
;
142 psf
->read_float
= replace_read_f
;
143 psf
->read_double
= replace_read_f2d
;
146 case (SF_ENDIAN_BIG
+ FLOAT_BROKEN_BE
) :
147 psf
->data_endswap
= SF_FALSE
;
148 psf
->read_short
= replace_read_f2s
;
149 psf
->read_int
= replace_read_f2i
;
150 psf
->read_float
= replace_read_f
;
151 psf
->read_double
= replace_read_f2d
;
154 case (SF_ENDIAN_LITTLE
+ FLOAT_BROKEN_BE
) :
155 psf
->data_endswap
= SF_TRUE
;
156 psf
->read_short
= replace_read_f2s
;
157 psf
->read_int
= replace_read_f2i
;
158 psf
->read_float
= replace_read_f
;
159 psf
->read_double
= replace_read_f2d
;
166 if (psf
->file
.mode
== SFM_WRITE
|| psf
->file
.mode
== SFM_RDWR
)
167 { switch (psf
->endian
+ float_caps
)
168 { case (SF_ENDIAN_LITTLE
+ FLOAT_CAN_RW_LE
) :
169 psf
->data_endswap
= SF_FALSE
;
170 psf
->write_short
= host_write_s2f
;
171 psf
->write_int
= host_write_i2f
;
172 psf
->write_float
= host_write_f
;
173 psf
->write_double
= host_write_d2f
;
176 case (SF_ENDIAN_BIG
+ FLOAT_CAN_RW_BE
) :
177 psf
->data_endswap
= SF_FALSE
;
178 psf
->write_short
= host_write_s2f
;
179 psf
->write_int
= host_write_i2f
;
180 psf
->write_float
= host_write_f
;
181 psf
->write_double
= host_write_d2f
;
184 case (SF_ENDIAN_BIG
+ FLOAT_CAN_RW_LE
) :
185 psf
->data_endswap
= SF_TRUE
;
186 psf
->write_short
= host_write_s2f
;
187 psf
->write_int
= host_write_i2f
;
188 psf
->write_float
= host_write_f
;
189 psf
->write_double
= host_write_d2f
;
192 case (SF_ENDIAN_LITTLE
+ FLOAT_CAN_RW_BE
) :
193 psf
->data_endswap
= SF_TRUE
;
194 psf
->write_short
= host_write_s2f
;
195 psf
->write_int
= host_write_i2f
;
196 psf
->write_float
= host_write_f
;
197 psf
->write_double
= host_write_d2f
;
200 /* When the CPU is not IEEE compatible. */
201 case (SF_ENDIAN_BIG
+ FLOAT_BROKEN_LE
) :
202 psf
->data_endswap
= SF_TRUE
;
203 psf
->write_short
= replace_write_s2f
;
204 psf
->write_int
= replace_write_i2f
;
205 psf
->write_float
= replace_write_f
;
206 psf
->write_double
= replace_write_d2f
;
209 case (SF_ENDIAN_LITTLE
+ FLOAT_BROKEN_LE
) :
210 psf
->data_endswap
= SF_FALSE
;
211 psf
->write_short
= replace_write_s2f
;
212 psf
->write_int
= replace_write_i2f
;
213 psf
->write_float
= replace_write_f
;
214 psf
->write_double
= replace_write_d2f
;
217 case (SF_ENDIAN_BIG
+ FLOAT_BROKEN_BE
) :
218 psf
->data_endswap
= SF_FALSE
;
219 psf
->write_short
= replace_write_s2f
;
220 psf
->write_int
= replace_write_i2f
;
221 psf
->write_float
= replace_write_f
;
222 psf
->write_double
= replace_write_d2f
;
225 case (SF_ENDIAN_LITTLE
+ FLOAT_BROKEN_BE
) :
226 psf
->data_endswap
= SF_TRUE
;
227 psf
->write_short
= replace_write_s2f
;
228 psf
->write_int
= replace_write_i2f
;
229 psf
->write_float
= replace_write_f
;
230 psf
->write_double
= replace_write_d2f
;
237 if (psf
->filelength
> psf
->dataoffset
)
238 { psf
->datalength
= (psf
->dataend
> 0) ? psf
->dataend
- psf
->dataoffset
:
239 psf
->filelength
- psf
->dataoffset
;
242 psf
->datalength
= 0 ;
244 psf
->sf
.frames
= psf
->blockwidth
> 0 ? psf
->datalength
/ psf
->blockwidth
: 0 ;
250 float32_be_read (unsigned char *cptr
)
251 { int exponent
, mantissa
, negative
;
254 negative
= cptr
[0] & 0x80 ;
255 exponent
= ((cptr
[0] & 0x7F) << 1) | ((cptr
[1] & 0x80) ? 1 : 0) ;
256 mantissa
= ((cptr
[1] & 0x7F) << 16) | (cptr
[2] << 8) | (cptr
[3]) ;
258 if (! (exponent
|| mantissa
))
261 mantissa
|= 0x800000 ;
262 exponent
= exponent
? exponent
- 127 : 0 ;
264 fvalue
= mantissa
? ((float) mantissa
) / ((float) 0x800000) : 0.0 ;
270 fvalue
*= pow (2.0, exponent
) ;
271 else if (exponent
< 0)
272 fvalue
/= pow (2.0, abs (exponent
)) ;
275 } /* float32_be_read */
278 float32_le_read (unsigned char *cptr
)
279 { int exponent
, mantissa
, negative
;
282 negative
= cptr
[3] & 0x80 ;
283 exponent
= ((cptr
[3] & 0x7F) << 1) | ((cptr
[2] & 0x80) ? 1 : 0) ;
284 mantissa
= ((cptr
[2] & 0x7F) << 16) | (cptr
[1] << 8) | (cptr
[0]) ;
286 if (! (exponent
|| mantissa
))
289 mantissa
|= 0x800000 ;
290 exponent
= exponent
? exponent
- 127 : 0 ;
292 fvalue
= mantissa
? ((float) mantissa
) / ((float) 0x800000) : 0.0 ;
298 fvalue
*= pow (2.0, exponent
) ;
299 else if (exponent
< 0)
300 fvalue
/= pow (2.0, abs (exponent
)) ;
303 } /* float32_le_read */
306 float32_le_write (float in
, unsigned char *out
)
307 { int exponent
, mantissa
, negative
= 0 ;
309 memset (out
, 0, sizeof (int)) ;
311 if (fabs (in
) < 1e-30)
319 in
= frexp (in
, &exponent
) ;
323 in
*= (float) 0x1000000 ;
324 mantissa
= (((int) in
) & 0x7FFFFF) ;
332 out
[0] = mantissa
& 0xFF ;
333 out
[1] = (mantissa
>> 8) & 0xFF ;
334 out
[2] |= (mantissa
>> 16) & 0x7F ;
335 out
[3] |= (exponent
>> 1) & 0x7F ;
338 } /* float32_le_write */
341 float32_be_write (float in
, unsigned char *out
)
342 { int exponent
, mantissa
, negative
= 0 ;
344 memset (out
, 0, sizeof (int)) ;
346 if (fabs (in
) < 1e-30)
354 in
= frexp (in
, &exponent
) ;
358 in
*= (float) 0x1000000 ;
359 mantissa
= (((int) in
) & 0x7FFFFF) ;
367 out
[3] = mantissa
& 0xFF ;
368 out
[2] = (mantissa
>> 8) & 0xFF ;
369 out
[1] |= (mantissa
>> 16) & 0x7F ;
370 out
[0] |= (exponent
>> 1) & 0x7F ;
373 } /* float32_be_write */
375 /*==============================================================================================
376 ** Private functions.
380 float32_peak_update (SF_PRIVATE
*psf
, const float *buffer
, int count
, sf_count_t indx
)
385 for (chan
= 0 ; chan
< psf
->sf
.channels
; chan
++)
386 { fmaxval
= fabs (buffer
[chan
]) ;
388 for (k
= chan
; k
< count
; k
+= psf
->sf
.channels
)
389 if (fmaxval
< fabs (buffer
[k
]))
390 { fmaxval
= fabs (buffer
[k
]) ;
394 if (fmaxval
> psf
->peak_info
->peaks
[chan
].value
)
395 { psf
->peak_info
->peaks
[chan
].value
= fmaxval
;
396 psf
->peak_info
->peaks
[chan
].position
= psf
->write_current
+ indx
+ (position
/ psf
->sf
.channels
) ;
401 } /* float32_peak_update */
404 float32_get_capability (SF_PRIVATE
*psf
)
408 unsigned char c
[4] ;
411 data
.f
= (float) 1.23456789 ; /* Some abitrary value. */
413 if (! psf
->ieee_replace
)
414 { /* If this test is true ints and floats are compatible and little endian. */
415 if (data
.c
[0] == 0x52 && data
.c
[1] == 0x06 && data
.c
[2] == 0x9e && data
.c
[3] == 0x3f)
416 return FLOAT_CAN_RW_LE
;
418 /* If this test is true ints and floats are compatible and big endian. */
419 if (data
.c
[3] == 0x52 && data
.c
[2] == 0x06 && data
.c
[1] == 0x9e && data
.c
[0] == 0x3f)
420 return FLOAT_CAN_RW_BE
;
423 /* Floats are broken. Don't expect reading or writing to be fast. */
424 psf_log_printf (psf
, "Using IEEE replacement code for float.\n") ;
426 return (CPU_IS_LITTLE_ENDIAN
) ? FLOAT_BROKEN_LE
: FLOAT_BROKEN_BE
;
427 } /* float32_get_capability */
429 /*=======================================================================================
433 f2s_array (const float *src
, int count
, short *dest
, float scale
)
436 { dest
[count
] = lrintf (scale
* src
[count
]) ;
441 f2s_clip_array (const float *src
, int count
, short *dest
, float scale
)
442 { while (--count
>= 0)
443 { float tmp
= scale
* src
[count
] ;
445 if (CPU_CLIPS_POSITIVE
== 0 && tmp
> 32767.0)
446 dest
[count
] = SHRT_MAX
;
447 else if (CPU_CLIPS_NEGATIVE
== 0 && tmp
< -32768.0)
448 dest
[count
] = SHRT_MIN
;
450 dest
[count
] = lrintf (tmp
) ;
452 } /* f2s_clip_array */
455 f2i_array (const float *src
, int count
, int *dest
, float scale
)
456 { while (--count
>= 0)
457 { dest
[count
] = lrintf (scale
* src
[count
]) ;
462 f2i_clip_array (const float *src
, int count
, int *dest
, float scale
)
463 { while (--count
>= 0)
464 { float tmp
= scale
* src
[count
] ;
466 if (CPU_CLIPS_POSITIVE
== 0 && tmp
> (1.0 * INT_MAX
))
467 dest
[count
] = INT_MAX
;
468 else if (CPU_CLIPS_NEGATIVE
== 0 && tmp
< (-1.0 * INT_MAX
))
469 dest
[count
] = INT_MIN
;
471 dest
[count
] = lrintf (tmp
) ;
473 } /* f2i_clip_array */
476 f2d_array (const float *src
, int count
, double *dest
)
477 { while (--count
>= 0)
478 { dest
[count
] = src
[count
] ;
483 s2f_array (const short *src
, float *dest
, int count
, float scale
)
484 { while (--count
>= 0)
485 { dest
[count
] = scale
* src
[count
] ;
490 i2f_array (const int *src
, float *dest
, int count
, float scale
)
491 { while (--count
>= 0)
492 { dest
[count
] = scale
* src
[count
] ;
497 d2f_array (const double *src
, float *dest
, int count
)
498 { while (--count
>= 0)
499 { dest
[count
] = src
[count
] ;
503 /*----------------------------------------------------------------------------------------------
507 host_read_f2s (SF_PRIVATE
*psf
, short *ptr
, sf_count_t len
)
508 { void (*convert
) (const float *, int, short *, float) ;
509 int bufferlen
, readcount
;
510 sf_count_t total
= 0 ;
513 convert
= (psf
->add_clipping
) ? f2s_clip_array
: f2s_array
;
514 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
515 scale
= (psf
->float_int_mult
== 0) ? 1.0 : 0x7FFF / psf
->float_max
;
518 { if (len
< bufferlen
)
519 bufferlen
= (int) len
;
520 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
522 /* Fix me : Need lef2s_array */
523 if (psf
->data_endswap
== SF_TRUE
)
524 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
526 convert (psf
->u
.fbuf
, readcount
, ptr
+ total
, scale
) ;
528 if (readcount
< bufferlen
)
534 } /* host_read_f2s */
537 host_read_f2i (SF_PRIVATE
*psf
, int *ptr
, sf_count_t len
)
538 { void (*convert
) (const float *, int, int *, float) ;
539 int bufferlen
, readcount
;
540 sf_count_t total
= 0 ;
543 convert
= (psf
->add_clipping
) ? f2i_clip_array
: f2i_array
;
544 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
545 scale
= (psf
->float_int_mult
== 0) ? 1.0 : 0x7FFFFFFF / psf
->float_max
;
548 { if (len
< bufferlen
)
549 bufferlen
= (int) len
;
550 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
552 if (psf
->data_endswap
== SF_TRUE
)
553 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
555 convert (psf
->u
.fbuf
, readcount
, ptr
+ total
, scale
) ;
557 if (readcount
< bufferlen
)
563 } /* host_read_f2i */
566 host_read_f (SF_PRIVATE
*psf
, float *ptr
, sf_count_t len
)
567 { int bufferlen
, readcount
;
568 sf_count_t total
= 0 ;
570 if (psf
->data_endswap
!= SF_TRUE
)
571 return psf_fread (ptr
, sizeof (float), len
, psf
) ;
573 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
576 { if (len
< bufferlen
)
577 bufferlen
= (int) len
;
578 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
580 endswap_int_copy ((int*) (ptr
+ total
), psf
->u
.ibuf
, readcount
) ;
583 if (readcount
< bufferlen
)
592 host_read_f2d (SF_PRIVATE
*psf
, double *ptr
, sf_count_t len
)
593 { int bufferlen
, readcount
;
594 sf_count_t total
= 0 ;
596 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
599 { if (len
< bufferlen
)
600 bufferlen
= (int) len
;
601 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
603 if (psf
->data_endswap
== SF_TRUE
)
604 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
606 /* Fix me : Need lef2d_array */
607 f2d_array (psf
->u
.fbuf
, readcount
, ptr
+ total
) ;
609 if (readcount
< bufferlen
)
615 } /* host_read_f2d */
618 host_write_s2f (SF_PRIVATE
*psf
, const short *ptr
, sf_count_t len
)
619 { int bufferlen
, writecount
;
620 sf_count_t total
= 0 ;
624 scale
= (psf
->scale_int_float
== 0) ? 1.0 : 1.0 / 0x8000 ;
625 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
628 { if (len
< bufferlen
)
629 bufferlen
= (int) len
;
630 s2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
, scale
) ;
633 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
635 if (psf
->data_endswap
== SF_TRUE
)
636 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
638 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
639 total
+= writecount
;
640 if (writecount
< bufferlen
)
646 } /* host_write_s2f */
649 host_write_i2f (SF_PRIVATE
*psf
, const int *ptr
, sf_count_t len
)
650 { int bufferlen
, writecount
;
651 sf_count_t total
= 0 ;
654 scale
= (psf
->scale_int_float
== 0) ? 1.0 : 1.0 / (8.0 * 0x10000000) ;
655 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
658 { if (len
< bufferlen
)
659 bufferlen
= (int) len
;
660 i2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
, scale
) ;
663 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
665 if (psf
->data_endswap
== SF_TRUE
)
666 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
668 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float) , bufferlen
, psf
) ;
669 total
+= writecount
;
670 if (writecount
< bufferlen
)
676 } /* host_write_i2f */
679 host_write_f (SF_PRIVATE
*psf
, const float *ptr
, sf_count_t len
)
680 { int bufferlen
, writecount
;
681 sf_count_t total
= 0 ;
684 float32_peak_update (psf
, ptr
, len
, 0) ;
686 if (psf
->data_endswap
!= SF_TRUE
)
687 return psf_fwrite (ptr
, sizeof (float), len
, psf
) ;
689 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
692 { if (len
< bufferlen
)
693 bufferlen
= (int) len
;
695 endswap_int_copy (psf
->u
.ibuf
, (const int*) (ptr
+ total
), bufferlen
) ;
697 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
698 total
+= writecount
;
699 if (writecount
< bufferlen
)
708 host_write_d2f (SF_PRIVATE
*psf
, const double *ptr
, sf_count_t len
)
709 { int bufferlen
, writecount
;
710 sf_count_t total
= 0 ;
712 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
715 { if (len
< bufferlen
)
716 bufferlen
= (int) len
;
718 d2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
) ;
721 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
723 if (psf
->data_endswap
== SF_TRUE
)
724 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
726 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
727 total
+= writecount
;
728 if (writecount
< bufferlen
)
734 } /* host_write_d2f */
736 /*=======================================================================================
740 replace_read_f2s (SF_PRIVATE
*psf
, short *ptr
, sf_count_t len
)
741 { int bufferlen
, readcount
;
742 sf_count_t total
= 0 ;
745 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
746 scale
= (psf
->float_int_mult
== 0) ? 1.0 : 0x7FFF / psf
->float_max
;
749 { if (len
< bufferlen
)
750 bufferlen
= (int) len
;
751 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
753 if (psf
->data_endswap
== SF_TRUE
)
754 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
756 bf2f_array (psf
->u
.fbuf
, bufferlen
) ;
758 f2s_array (psf
->u
.fbuf
, readcount
, ptr
+ total
, scale
) ;
760 if (readcount
< bufferlen
)
766 } /* replace_read_f2s */
769 replace_read_f2i (SF_PRIVATE
*psf
, int *ptr
, sf_count_t len
)
770 { int bufferlen
, readcount
;
771 sf_count_t total
= 0 ;
774 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
775 scale
= (psf
->float_int_mult
== 0) ? 1.0 : 0x7FFF / psf
->float_max
;
778 { if (len
< bufferlen
)
779 bufferlen
= (int) len
;
780 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
782 if (psf
->data_endswap
== SF_TRUE
)
783 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
785 bf2f_array (psf
->u
.fbuf
, bufferlen
) ;
787 f2i_array (psf
->u
.fbuf
, readcount
, ptr
+ total
, scale
) ;
789 if (readcount
< bufferlen
)
795 } /* replace_read_f2i */
798 replace_read_f (SF_PRIVATE
*psf
, float *ptr
, sf_count_t len
)
799 { int bufferlen
, readcount
;
800 sf_count_t total
= 0 ;
804 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
807 { if (len
< bufferlen
)
808 bufferlen
= (int) len
;
809 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
811 if (psf
->data_endswap
== SF_TRUE
)
812 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
814 bf2f_array (psf
->u
.fbuf
, bufferlen
) ;
816 memcpy (ptr
+ total
, psf
->u
.fbuf
, bufferlen
* sizeof (float)) ;
819 if (readcount
< bufferlen
)
825 } /* replace_read_f */
828 replace_read_f2d (SF_PRIVATE
*psf
, double *ptr
, sf_count_t len
)
829 { int bufferlen
, readcount
;
830 sf_count_t total
= 0 ;
832 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
835 { if (len
< bufferlen
)
836 bufferlen
= (int) len
;
837 readcount
= psf_fread (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
839 if (psf
->data_endswap
== SF_TRUE
)
840 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
842 bf2f_array (psf
->u
.fbuf
, bufferlen
) ;
844 f2d_array (psf
->u
.fbuf
, readcount
, ptr
+ total
) ;
846 if (readcount
< bufferlen
)
852 } /* replace_read_f2d */
855 replace_write_s2f (SF_PRIVATE
*psf
, const short *ptr
, sf_count_t len
)
856 { int bufferlen
, writecount
;
857 sf_count_t total
= 0 ;
860 scale
= (psf
->scale_int_float
== 0) ? 1.0 : 1.0 / 0x8000 ;
861 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
864 { if (len
< bufferlen
)
865 bufferlen
= (int) len
;
866 s2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
, scale
) ;
869 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
871 f2bf_array (psf
->u
.fbuf
, bufferlen
) ;
873 if (psf
->data_endswap
== SF_TRUE
)
874 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
876 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
877 total
+= writecount
;
878 if (writecount
< bufferlen
)
884 } /* replace_write_s2f */
887 replace_write_i2f (SF_PRIVATE
*psf
, const int *ptr
, sf_count_t len
)
888 { int bufferlen
, writecount
;
889 sf_count_t total
= 0 ;
892 scale
= (psf
->scale_int_float
== 0) ? 1.0 : 1.0 / (8.0 * 0x10000000) ;
893 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
896 { if (len
< bufferlen
)
897 bufferlen
= (int) len
;
898 i2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
, scale
) ;
901 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
903 f2bf_array (psf
->u
.fbuf
, bufferlen
) ;
905 if (psf
->data_endswap
== SF_TRUE
)
906 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
908 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
909 total
+= writecount
;
910 if (writecount
< bufferlen
)
916 } /* replace_write_i2f */
919 replace_write_f (SF_PRIVATE
*psf
, const float *ptr
, sf_count_t len
)
920 { int bufferlen
, writecount
;
921 sf_count_t total
= 0 ;
925 float32_peak_update (psf
, ptr
, len
, 0) ;
927 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
930 { if (len
< bufferlen
)
931 bufferlen
= (int) len
;
933 memcpy (psf
->u
.fbuf
, ptr
+ total
, bufferlen
* sizeof (float)) ;
935 f2bf_array (psf
->u
.fbuf
, bufferlen
) ;
937 if (psf
->data_endswap
== SF_TRUE
)
938 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
940 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float) , bufferlen
, psf
) ;
941 total
+= writecount
;
942 if (writecount
< bufferlen
)
948 } /* replace_write_f */
951 replace_write_d2f (SF_PRIVATE
*psf
, const double *ptr
, sf_count_t len
)
952 { int bufferlen
, writecount
;
953 sf_count_t total
= 0 ;
955 bufferlen
= ARRAY_LEN (psf
->u
.fbuf
) ;
958 { if (len
< bufferlen
)
959 bufferlen
= (int) len
;
960 d2f_array (ptr
+ total
, psf
->u
.fbuf
, bufferlen
) ;
963 float32_peak_update (psf
, psf
->u
.fbuf
, bufferlen
, total
/ psf
->sf
.channels
) ;
965 f2bf_array (psf
->u
.fbuf
, bufferlen
) ;
967 if (psf
->data_endswap
== SF_TRUE
)
968 endswap_int_array (psf
->u
.ibuf
, bufferlen
) ;
970 writecount
= psf_fwrite (psf
->u
.fbuf
, sizeof (float), bufferlen
, psf
) ;
971 total
+= writecount
;
972 if (writecount
< bufferlen
)
978 } /* replace_write_d2f */
980 /*----------------------------------------------------------------------------------------------
984 bf2f_array (float *buffer
, int count
)
985 { while (--count
>= 0)
986 { buffer
[count
] = FLOAT32_READ ((unsigned char *) (buffer
+ count
)) ;
991 f2bf_array (float *buffer
, int count
)
992 { while (--count
>= 0)
993 { FLOAT32_WRITE (buffer
[count
], (unsigned char*) (buffer
+ count
)) ;