github.com/Konstantin8105/c4go@v0.0.0-20240505174241-768bb1c65a51/tests/raylib/external/dr_mp3.h (about) 1 /* 2 MP3 audio decoder. Choice of public domain or MIT-0. See license statements at the end of this file. 3 dr_mp3 - v0.6.31 - 2021-08-22 4 5 David Reid - mackron@gmail.com 6 7 GitHub: https://github.com/mackron/dr_libs 8 9 Based on minimp3 (https://github.com/lieff/minimp3) which is where the real work was done. See the bottom of this file for differences between minimp3 and dr_mp3. 10 */ 11 12 /* 13 RELEASE NOTES - VERSION 0.6 14 =========================== 15 Version 0.6 includes breaking changes with the configuration of decoders. The ability to customize the number of output channels and the sample rate has been 16 removed. You must now use the channel count and sample rate reported by the MP3 stream itself, and all channel and sample rate conversion must be done 17 yourself. 18 19 20 Changes to Initialization 21 ------------------------- 22 Previously, `drmp3_init()`, etc. took a pointer to a `drmp3_config` object that allowed you to customize the output channels and sample rate. This has been 23 removed. If you need the old behaviour you will need to convert the data yourself or just not upgrade. The following APIs have changed. 24 25 `drmp3_init()` 26 `drmp3_init_memory()` 27 `drmp3_init_file()` 28 29 30 Miscellaneous Changes 31 --------------------- 32 Support for loading a file from a `wchar_t` string has been added via the `drmp3_init_file_w()` API. 33 */ 34 35 /* 36 Introducation 37 ============= 38 dr_mp3 is a single file library. To use it, do something like the following in one .c file. 39 40 ```c 41 #define DR_MP3_IMPLEMENTATION 42 #include "dr_mp3.h" 43 ``` 44 45 You can then #include this file in other parts of the program as you would with any other header file. To decode audio data, do something like the following: 46 47 ```c 48 drmp3 mp3; 49 if (!drmp3_init_file(&mp3, "MySong.mp3", NULL)) { 50 // Failed to open file 51 } 52 53 ... 54 55 drmp3_uint64 framesRead = drmp3_read_pcm_frames_f32(pMP3, framesToRead, pFrames); 56 ``` 57 58 The drmp3 object is transparent so you can get access to the channel count and sample rate like so: 59 60 ``` 61 drmp3_uint32 channels = mp3.channels; 62 drmp3_uint32 sampleRate = mp3.sampleRate; 63 ``` 64 65 The example above initializes a decoder from a file, but you can also initialize it from a block of memory and read and seek callbacks with 66 `drmp3_init_memory()` and `drmp3_init()` respectively. 67 68 You do not need to do any annoying memory management when reading PCM frames - this is all managed internally. You can request any number of PCM frames in each 69 call to `drmp3_read_pcm_frames_f32()` and it will return as many PCM frames as it can, up to the requested amount. 70 71 You can also decode an entire file in one go with `drmp3_open_and_read_pcm_frames_f32()`, `drmp3_open_memory_and_read_pcm_frames_f32()` and 72 `drmp3_open_file_and_read_pcm_frames_f32()`. 73 74 75 Build Options 76 ============= 77 #define these options before including this file. 78 79 #define DR_MP3_NO_STDIO 80 Disable drmp3_init_file(), etc. 81 82 #define DR_MP3_NO_SIMD 83 Disable SIMD optimizations. 84 */ 85 86 #ifndef dr_mp3_h 87 #define dr_mp3_h 88 89 #ifdef __cplusplus 90 extern "C" { 91 #endif 92 93 #define DRMP3_STRINGIFY(x) #x 94 #define DRMP3_XSTRINGIFY(x) DRMP3_STRINGIFY(x) 95 96 #define DRMP3_VERSION_MAJOR 0 97 #define DRMP3_VERSION_MINOR 6 98 #define DRMP3_VERSION_REVISION 31 99 #define DRMP3_VERSION_STRING DRMP3_XSTRINGIFY(DRMP3_VERSION_MAJOR) "." DRMP3_XSTRINGIFY(DRMP3_VERSION_MINOR) "." DRMP3_XSTRINGIFY(DRMP3_VERSION_REVISION) 100 101 #include <stddef.h> /* For size_t. */ 102 103 /* Sized types. */ 104 typedef signed char drmp3_int8; 105 typedef unsigned char drmp3_uint8; 106 typedef signed short drmp3_int16; 107 typedef unsigned short drmp3_uint16; 108 typedef signed int drmp3_int32; 109 typedef unsigned int drmp3_uint32; 110 #if defined(_MSC_VER) 111 typedef signed __int64 drmp3_int64; 112 typedef unsigned __int64 drmp3_uint64; 113 #else 114 #if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) 115 #pragma GCC diagnostic push 116 #pragma GCC diagnostic ignored "-Wlong-long" 117 #if defined(__clang__) 118 #pragma GCC diagnostic ignored "-Wc++11-long-long" 119 #endif 120 #endif 121 typedef signed long long drmp3_int64; 122 typedef unsigned long long drmp3_uint64; 123 #if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) 124 #pragma GCC diagnostic pop 125 #endif 126 #endif 127 #if defined(__LP64__) || defined(_WIN64) || (defined(__x86_64__) && !defined(__ILP32__)) || defined(_M_X64) || defined(__ia64) || defined (_M_IA64) || defined(__aarch64__) || defined(_M_ARM64) || defined(__powerpc64__) 128 typedef drmp3_uint64 drmp3_uintptr; 129 #else 130 typedef drmp3_uint32 drmp3_uintptr; 131 #endif 132 typedef drmp3_uint8 drmp3_bool8; 133 typedef drmp3_uint32 drmp3_bool32; 134 #define DRMP3_TRUE 1 135 #define DRMP3_FALSE 0 136 137 #if !defined(DRMP3_API) 138 #if defined(DRMP3_DLL) 139 #if defined(_WIN32) 140 #define DRMP3_DLL_IMPORT __declspec(dllimport) 141 #define DRMP3_DLL_EXPORT __declspec(dllexport) 142 #define DRMP3_DLL_PRIVATE static 143 #else 144 #if defined(__GNUC__) && __GNUC__ >= 4 145 #define DRMP3_DLL_IMPORT __attribute__((visibility("default"))) 146 #define DRMP3_DLL_EXPORT __attribute__((visibility("default"))) 147 #define DRMP3_DLL_PRIVATE __attribute__((visibility("hidden"))) 148 #else 149 #define DRMP3_DLL_IMPORT 150 #define DRMP3_DLL_EXPORT 151 #define DRMP3_DLL_PRIVATE static 152 #endif 153 #endif 154 155 #if defined(DR_MP3_IMPLEMENTATION) || defined(DRMP3_IMPLEMENTATION) 156 #define DRMP3_API DRMP3_DLL_EXPORT 157 #else 158 #define DRMP3_API DRMP3_DLL_IMPORT 159 #endif 160 #define DRMP3_PRIVATE DRMP3_DLL_PRIVATE 161 #else 162 #define DRMP3_API extern 163 #define DRMP3_PRIVATE static 164 #endif 165 #endif 166 167 typedef drmp3_int32 drmp3_result; 168 #define DRMP3_SUCCESS 0 169 #define DRMP3_ERROR -1 /* A generic error. */ 170 #define DRMP3_INVALID_ARGS -2 171 #define DRMP3_INVALID_OPERATION -3 172 #define DRMP3_OUT_OF_MEMORY -4 173 #define DRMP3_OUT_OF_RANGE -5 174 #define DRMP3_ACCESS_DENIED -6 175 #define DRMP3_DOES_NOT_EXIST -7 176 #define DRMP3_ALREADY_EXISTS -8 177 #define DRMP3_TOO_MANY_OPEN_FILES -9 178 #define DRMP3_INVALID_FILE -10 179 #define DRMP3_TOO_BIG -11 180 #define DRMP3_PATH_TOO_LONG -12 181 #define DRMP3_NAME_TOO_LONG -13 182 #define DRMP3_NOT_DIRECTORY -14 183 #define DRMP3_IS_DIRECTORY -15 184 #define DRMP3_DIRECTORY_NOT_EMPTY -16 185 #define DRMP3_END_OF_FILE -17 186 #define DRMP3_NO_SPACE -18 187 #define DRMP3_BUSY -19 188 #define DRMP3_IO_ERROR -20 189 #define DRMP3_INTERRUPT -21 190 #define DRMP3_UNAVAILABLE -22 191 #define DRMP3_ALREADY_IN_USE -23 192 #define DRMP3_BAD_ADDRESS -24 193 #define DRMP3_BAD_SEEK -25 194 #define DRMP3_BAD_PIPE -26 195 #define DRMP3_DEADLOCK -27 196 #define DRMP3_TOO_MANY_LINKS -28 197 #define DRMP3_NOT_IMPLEMENTED -29 198 #define DRMP3_NO_MESSAGE -30 199 #define DRMP3_BAD_MESSAGE -31 200 #define DRMP3_NO_DATA_AVAILABLE -32 201 #define DRMP3_INVALID_DATA -33 202 #define DRMP3_TIMEOUT -34 203 #define DRMP3_NO_NETWORK -35 204 #define DRMP3_NOT_UNIQUE -36 205 #define DRMP3_NOT_SOCKET -37 206 #define DRMP3_NO_ADDRESS -38 207 #define DRMP3_BAD_PROTOCOL -39 208 #define DRMP3_PROTOCOL_UNAVAILABLE -40 209 #define DRMP3_PROTOCOL_NOT_SUPPORTED -41 210 #define DRMP3_PROTOCOL_FAMILY_NOT_SUPPORTED -42 211 #define DRMP3_ADDRESS_FAMILY_NOT_SUPPORTED -43 212 #define DRMP3_SOCKET_NOT_SUPPORTED -44 213 #define DRMP3_CONNECTION_RESET -45 214 #define DRMP3_ALREADY_CONNECTED -46 215 #define DRMP3_NOT_CONNECTED -47 216 #define DRMP3_CONNECTION_REFUSED -48 217 #define DRMP3_NO_HOST -49 218 #define DRMP3_IN_PROGRESS -50 219 #define DRMP3_CANCELLED -51 220 #define DRMP3_MEMORY_ALREADY_MAPPED -52 221 #define DRMP3_AT_END -53 222 223 224 #define DRMP3_MAX_PCM_FRAMES_PER_MP3_FRAME 1152 225 #define DRMP3_MAX_SAMPLES_PER_FRAME (DRMP3_MAX_PCM_FRAMES_PER_MP3_FRAME*2) 226 227 #ifdef _MSC_VER 228 #define DRMP3_INLINE __forceinline 229 #elif defined(__GNUC__) 230 /* 231 I've had a bug report where GCC is emitting warnings about functions possibly not being inlineable. This warning happens when 232 the __attribute__((always_inline)) attribute is defined without an "inline" statement. I think therefore there must be some 233 case where "__inline__" is not always defined, thus the compiler emitting these warnings. When using -std=c89 or -ansi on the 234 command line, we cannot use the "inline" keyword and instead need to use "__inline__". In an attempt to work around this issue 235 I am using "__inline__" only when we're compiling in strict ANSI mode. 236 */ 237 #if defined(__STRICT_ANSI__) 238 #define DRMP3_INLINE __inline__ __attribute__((always_inline)) 239 #else 240 #define DRMP3_INLINE inline __attribute__((always_inline)) 241 #endif 242 #elif defined(__WATCOMC__) 243 #define DRMP3_INLINE __inline 244 #else 245 #define DRMP3_INLINE 246 #endif 247 248 249 DRMP3_API void drmp3_version(drmp3_uint32* pMajor, drmp3_uint32* pMinor, drmp3_uint32* pRevision); 250 DRMP3_API const char* drmp3_version_string(void); 251 252 253 /* 254 Low Level Push API 255 ================== 256 */ 257 typedef struct 258 { 259 int frame_bytes, channels, hz, layer, bitrate_kbps; 260 } drmp3dec_frame_info; 261 262 typedef struct 263 { 264 float mdct_overlap[2][9*32], qmf_state[15*2*32]; 265 int reserv, free_format_bytes; 266 drmp3_uint8 header[4], reserv_buf[511]; 267 } drmp3dec; 268 269 /* Initializes a low level decoder. */ 270 DRMP3_API void drmp3dec_init(drmp3dec *dec); 271 272 /* Reads a frame from a low level decoder. */ 273 DRMP3_API int drmp3dec_decode_frame(drmp3dec *dec, const drmp3_uint8 *mp3, int mp3_bytes, void *pcm, drmp3dec_frame_info *info); 274 275 /* Helper for converting between f32 and s16. */ 276 DRMP3_API void drmp3dec_f32_to_s16(const float *in, drmp3_int16 *out, size_t num_samples); 277 278 279 280 /* 281 Main API (Pull API) 282 =================== 283 */ 284 typedef enum 285 { 286 drmp3_seek_origin_start, 287 drmp3_seek_origin_current 288 } drmp3_seek_origin; 289 290 typedef struct 291 { 292 drmp3_uint64 seekPosInBytes; /* Points to the first byte of an MP3 frame. */ 293 drmp3_uint64 pcmFrameIndex; /* The index of the PCM frame this seek point targets. */ 294 drmp3_uint16 mp3FramesToDiscard; /* The number of whole MP3 frames to be discarded before pcmFramesToDiscard. */ 295 drmp3_uint16 pcmFramesToDiscard; /* The number of leading samples to read and discard. These are discarded after mp3FramesToDiscard. */ 296 } drmp3_seek_point; 297 298 /* 299 Callback for when data is read. Return value is the number of bytes actually read. 300 301 pUserData [in] The user data that was passed to drmp3_init(), drmp3_open() and family. 302 pBufferOut [out] The output buffer. 303 bytesToRead [in] The number of bytes to read. 304 305 Returns the number of bytes actually read. 306 307 A return value of less than bytesToRead indicates the end of the stream. Do _not_ return from this callback until 308 either the entire bytesToRead is filled or you have reached the end of the stream. 309 */ 310 typedef size_t (* drmp3_read_proc)(void* pUserData, void* pBufferOut, size_t bytesToRead); 311 312 /* 313 Callback for when data needs to be seeked. 314 315 pUserData [in] The user data that was passed to drmp3_init(), drmp3_open() and family. 316 offset [in] The number of bytes to move, relative to the origin. Will never be negative. 317 origin [in] The origin of the seek - the current position or the start of the stream. 318 319 Returns whether or not the seek was successful. 320 321 Whether or not it is relative to the beginning or current position is determined by the "origin" parameter which 322 will be either drmp3_seek_origin_start or drmp3_seek_origin_current. 323 */ 324 typedef drmp3_bool32 (* drmp3_seek_proc)(void* pUserData, int offset, drmp3_seek_origin origin); 325 326 typedef struct 327 { 328 void* pUserData; 329 void* (* onMalloc)(size_t sz, void* pUserData); 330 void* (* onRealloc)(void* p, size_t sz, void* pUserData); 331 void (* onFree)(void* p, void* pUserData); 332 } drmp3_allocation_callbacks; 333 334 typedef struct 335 { 336 drmp3_uint32 channels; 337 drmp3_uint32 sampleRate; 338 } drmp3_config; 339 340 typedef struct 341 { 342 drmp3dec decoder; 343 drmp3dec_frame_info frameInfo; 344 drmp3_uint32 channels; 345 drmp3_uint32 sampleRate; 346 drmp3_read_proc onRead; 347 drmp3_seek_proc onSeek; 348 void* pUserData; 349 drmp3_allocation_callbacks allocationCallbacks; 350 drmp3_uint32 mp3FrameChannels; /* The number of channels in the currently loaded MP3 frame. Internal use only. */ 351 drmp3_uint32 mp3FrameSampleRate; /* The sample rate of the currently loaded MP3 frame. Internal use only. */ 352 drmp3_uint32 pcmFramesConsumedInMP3Frame; 353 drmp3_uint32 pcmFramesRemainingInMP3Frame; 354 drmp3_uint8 pcmFrames[sizeof(float)*DRMP3_MAX_SAMPLES_PER_FRAME]; /* <-- Multipled by sizeof(float) to ensure there's enough room for DR_MP3_FLOAT_OUTPUT. */ 355 drmp3_uint64 currentPCMFrame; /* The current PCM frame, globally, based on the output sample rate. Mainly used for seeking. */ 356 drmp3_uint64 streamCursor; /* The current byte the decoder is sitting on in the raw stream. */ 357 drmp3_seek_point* pSeekPoints; /* NULL by default. Set with drmp3_bind_seek_table(). Memory is owned by the client. dr_mp3 will never attempt to free this pointer. */ 358 drmp3_uint32 seekPointCount; /* The number of items in pSeekPoints. When set to 0 assumes to no seek table. Defaults to zero. */ 359 size_t dataSize; 360 size_t dataCapacity; 361 size_t dataConsumed; 362 drmp3_uint8* pData; 363 drmp3_bool32 atEnd : 1; 364 struct 365 { 366 const drmp3_uint8* pData; 367 size_t dataSize; 368 size_t currentReadPos; 369 } memory; /* Only used for decoders that were opened against a block of memory. */ 370 } drmp3; 371 372 /* 373 Initializes an MP3 decoder. 374 375 onRead [in] The function to call when data needs to be read from the client. 376 onSeek [in] The function to call when the read position of the client data needs to move. 377 pUserData [in, optional] A pointer to application defined data that will be passed to onRead and onSeek. 378 379 Returns true if successful; false otherwise. 380 381 Close the loader with drmp3_uninit(). 382 383 See also: drmp3_init_file(), drmp3_init_memory(), drmp3_uninit() 384 */ 385 DRMP3_API drmp3_bool32 drmp3_init(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks); 386 387 /* 388 Initializes an MP3 decoder from a block of memory. 389 390 This does not create a copy of the data. It is up to the application to ensure the buffer remains valid for 391 the lifetime of the drmp3 object. 392 393 The buffer should contain the contents of the entire MP3 file. 394 */ 395 DRMP3_API drmp3_bool32 drmp3_init_memory(drmp3* pMP3, const void* pData, size_t dataSize, const drmp3_allocation_callbacks* pAllocationCallbacks); 396 397 #ifndef DR_MP3_NO_STDIO 398 /* 399 Initializes an MP3 decoder from a file. 400 401 This holds the internal FILE object until drmp3_uninit() is called. Keep this in mind if you're caching drmp3 402 objects because the operating system may restrict the number of file handles an application can have open at 403 any given time. 404 */ 405 DRMP3_API drmp3_bool32 drmp3_init_file(drmp3* pMP3, const char* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks); 406 DRMP3_API drmp3_bool32 drmp3_init_file_w(drmp3* pMP3, const wchar_t* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks); 407 #endif 408 409 /* 410 Uninitializes an MP3 decoder. 411 */ 412 DRMP3_API void drmp3_uninit(drmp3* pMP3); 413 414 /* 415 Reads PCM frames as interleaved 32-bit IEEE floating point PCM. 416 417 Note that framesToRead specifies the number of PCM frames to read, _not_ the number of MP3 frames. 418 */ 419 DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_f32(drmp3* pMP3, drmp3_uint64 framesToRead, float* pBufferOut); 420 421 /* 422 Reads PCM frames as interleaved signed 16-bit integer PCM. 423 424 Note that framesToRead specifies the number of PCM frames to read, _not_ the number of MP3 frames. 425 */ 426 DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_s16(drmp3* pMP3, drmp3_uint64 framesToRead, drmp3_int16* pBufferOut); 427 428 /* 429 Seeks to a specific frame. 430 431 Note that this is _not_ an MP3 frame, but rather a PCM frame. 432 */ 433 DRMP3_API drmp3_bool32 drmp3_seek_to_pcm_frame(drmp3* pMP3, drmp3_uint64 frameIndex); 434 435 /* 436 Calculates the total number of PCM frames in the MP3 stream. Cannot be used for infinite streams such as internet 437 radio. Runs in linear time. Returns 0 on error. 438 */ 439 DRMP3_API drmp3_uint64 drmp3_get_pcm_frame_count(drmp3* pMP3); 440 441 /* 442 Calculates the total number of MP3 frames in the MP3 stream. Cannot be used for infinite streams such as internet 443 radio. Runs in linear time. Returns 0 on error. 444 */ 445 DRMP3_API drmp3_uint64 drmp3_get_mp3_frame_count(drmp3* pMP3); 446 447 /* 448 Calculates the total number of MP3 and PCM frames in the MP3 stream. Cannot be used for infinite streams such as internet 449 radio. Runs in linear time. Returns 0 on error. 450 451 This is equivalent to calling drmp3_get_mp3_frame_count() and drmp3_get_pcm_frame_count() except that it's more efficient. 452 */ 453 DRMP3_API drmp3_bool32 drmp3_get_mp3_and_pcm_frame_count(drmp3* pMP3, drmp3_uint64* pMP3FrameCount, drmp3_uint64* pPCMFrameCount); 454 455 /* 456 Calculates the seekpoints based on PCM frames. This is slow. 457 458 pSeekpoint count is a pointer to a uint32 containing the seekpoint count. On input it contains the desired count. 459 On output it contains the actual count. The reason for this design is that the client may request too many 460 seekpoints, in which case dr_mp3 will return a corrected count. 461 462 Note that seektable seeking is not quite sample exact when the MP3 stream contains inconsistent sample rates. 463 */ 464 DRMP3_API drmp3_bool32 drmp3_calculate_seek_points(drmp3* pMP3, drmp3_uint32* pSeekPointCount, drmp3_seek_point* pSeekPoints); 465 466 /* 467 Binds a seek table to the decoder. 468 469 This does _not_ make a copy of pSeekPoints - it only references it. It is up to the application to ensure this 470 remains valid while it is bound to the decoder. 471 472 Use drmp3_calculate_seek_points() to calculate the seek points. 473 */ 474 DRMP3_API drmp3_bool32 drmp3_bind_seek_table(drmp3* pMP3, drmp3_uint32 seekPointCount, drmp3_seek_point* pSeekPoints); 475 476 477 /* 478 Opens an decodes an entire MP3 stream as a single operation. 479 480 On output pConfig will receive the channel count and sample rate of the stream. 481 482 Free the returned pointer with drmp3_free(). 483 */ 484 DRMP3_API float* drmp3_open_and_read_pcm_frames_f32(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 485 DRMP3_API drmp3_int16* drmp3_open_and_read_pcm_frames_s16(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 486 487 DRMP3_API float* drmp3_open_memory_and_read_pcm_frames_f32(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 488 DRMP3_API drmp3_int16* drmp3_open_memory_and_read_pcm_frames_s16(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 489 490 #ifndef DR_MP3_NO_STDIO 491 DRMP3_API float* drmp3_open_file_and_read_pcm_frames_f32(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 492 DRMP3_API drmp3_int16* drmp3_open_file_and_read_pcm_frames_s16(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); 493 #endif 494 495 /* 496 Allocates a block of memory on the heap. 497 */ 498 DRMP3_API void* drmp3_malloc(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks); 499 500 /* 501 Frees any memory that was allocated by a public drmp3 API. 502 */ 503 DRMP3_API void drmp3_free(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks); 504 505 #ifdef __cplusplus 506 } 507 #endif 508 #endif /* dr_mp3_h */ 509 510 511 /************************************************************************************************************************************************************ 512 ************************************************************************************************************************************************************ 513 514 IMPLEMENTATION 515 516 ************************************************************************************************************************************************************ 517 ************************************************************************************************************************************************************/ 518 #if defined(DR_MP3_IMPLEMENTATION) || defined(DRMP3_IMPLEMENTATION) 519 #ifndef dr_mp3_c 520 #define dr_mp3_c 521 522 #include <stdlib.h> 523 #include <string.h> 524 #include <limits.h> /* For INT_MAX */ 525 526 DRMP3_API void drmp3_version(drmp3_uint32* pMajor, drmp3_uint32* pMinor, drmp3_uint32* pRevision) 527 { 528 if (pMajor) { 529 *pMajor = DRMP3_VERSION_MAJOR; 530 } 531 532 if (pMinor) { 533 *pMinor = DRMP3_VERSION_MINOR; 534 } 535 536 if (pRevision) { 537 *pRevision = DRMP3_VERSION_REVISION; 538 } 539 } 540 541 DRMP3_API const char* drmp3_version_string(void) 542 { 543 return DRMP3_VERSION_STRING; 544 } 545 546 /* Disable SIMD when compiling with TCC for now. */ 547 #if defined(__TINYC__) 548 #define DR_MP3_NO_SIMD 549 #endif 550 551 #define DRMP3_OFFSET_PTR(p, offset) ((void*)((drmp3_uint8*)(p) + (offset))) 552 553 #define DRMP3_MAX_FREE_FORMAT_FRAME_SIZE 2304 /* more than ISO spec's */ 554 #ifndef DRMP3_MAX_FRAME_SYNC_MATCHES 555 #define DRMP3_MAX_FRAME_SYNC_MATCHES 10 556 #endif 557 558 #define DRMP3_MAX_L3_FRAME_PAYLOAD_BYTES DRMP3_MAX_FREE_FORMAT_FRAME_SIZE /* MUST be >= 320000/8/32000*1152 = 1440 */ 559 560 #define DRMP3_MAX_BITRESERVOIR_BYTES 511 561 #define DRMP3_SHORT_BLOCK_TYPE 2 562 #define DRMP3_STOP_BLOCK_TYPE 3 563 #define DRMP3_MODE_MONO 3 564 #define DRMP3_MODE_JOINT_STEREO 1 565 #define DRMP3_HDR_SIZE 4 566 #define DRMP3_HDR_IS_MONO(h) (((h[3]) & 0xC0) == 0xC0) 567 #define DRMP3_HDR_IS_MS_STEREO(h) (((h[3]) & 0xE0) == 0x60) 568 #define DRMP3_HDR_IS_FREE_FORMAT(h) (((h[2]) & 0xF0) == 0) 569 #define DRMP3_HDR_IS_CRC(h) (!((h[1]) & 1)) 570 #define DRMP3_HDR_TEST_PADDING(h) ((h[2]) & 0x2) 571 #define DRMP3_HDR_TEST_MPEG1(h) ((h[1]) & 0x8) 572 #define DRMP3_HDR_TEST_NOT_MPEG25(h) ((h[1]) & 0x10) 573 #define DRMP3_HDR_TEST_I_STEREO(h) ((h[3]) & 0x10) 574 #define DRMP3_HDR_TEST_MS_STEREO(h) ((h[3]) & 0x20) 575 #define DRMP3_HDR_GET_STEREO_MODE(h) (((h[3]) >> 6) & 3) 576 #define DRMP3_HDR_GET_STEREO_MODE_EXT(h) (((h[3]) >> 4) & 3) 577 #define DRMP3_HDR_GET_LAYER(h) (((h[1]) >> 1) & 3) 578 #define DRMP3_HDR_GET_BITRATE(h) ((h[2]) >> 4) 579 #define DRMP3_HDR_GET_SAMPLE_RATE(h) (((h[2]) >> 2) & 3) 580 #define DRMP3_HDR_GET_MY_SAMPLE_RATE(h) (DRMP3_HDR_GET_SAMPLE_RATE(h) + (((h[1] >> 3) & 1) + ((h[1] >> 4) & 1))*3) 581 #define DRMP3_HDR_IS_FRAME_576(h) ((h[1] & 14) == 2) 582 #define DRMP3_HDR_IS_LAYER_1(h) ((h[1] & 6) == 6) 583 584 #define DRMP3_BITS_DEQUANTIZER_OUT -1 585 #define DRMP3_MAX_SCF (255 + DRMP3_BITS_DEQUANTIZER_OUT*4 - 210) 586 #define DRMP3_MAX_SCFI ((DRMP3_MAX_SCF + 3) & ~3) 587 588 #define DRMP3_MIN(a, b) ((a) > (b) ? (b) : (a)) 589 #define DRMP3_MAX(a, b) ((a) < (b) ? (b) : (a)) 590 591 #if !defined(DR_MP3_NO_SIMD) 592 593 #if !defined(DR_MP3_ONLY_SIMD) && (defined(_M_X64) || defined(__x86_64__) || defined(__aarch64__) || defined(_M_ARM64)) 594 /* x64 always have SSE2, arm64 always have neon, no need for generic code */ 595 #define DR_MP3_ONLY_SIMD 596 #endif 597 598 #if ((defined(_MSC_VER) && _MSC_VER >= 1400) && (defined(_M_IX86) || defined(_M_X64))) || ((defined(__i386__) || defined(__x86_64__)) && defined(__SSE2__)) 599 #if defined(_MSC_VER) 600 #include <intrin.h> 601 #endif 602 #include <emmintrin.h> 603 #define DRMP3_HAVE_SSE 1 604 #define DRMP3_HAVE_SIMD 1 605 #define DRMP3_VSTORE _mm_storeu_ps 606 #define DRMP3_VLD _mm_loadu_ps 607 #define DRMP3_VSET _mm_set1_ps 608 #define DRMP3_VADD _mm_add_ps 609 #define DRMP3_VSUB _mm_sub_ps 610 #define DRMP3_VMUL _mm_mul_ps 611 #define DRMP3_VMAC(a, x, y) _mm_add_ps(a, _mm_mul_ps(x, y)) 612 #define DRMP3_VMSB(a, x, y) _mm_sub_ps(a, _mm_mul_ps(x, y)) 613 #define DRMP3_VMUL_S(x, s) _mm_mul_ps(x, _mm_set1_ps(s)) 614 #define DRMP3_VREV(x) _mm_shuffle_ps(x, x, _MM_SHUFFLE(0, 1, 2, 3)) 615 typedef __m128 drmp3_f4; 616 #if defined(_MSC_VER) || defined(DR_MP3_ONLY_SIMD) 617 #define drmp3_cpuid __cpuid 618 #else 619 static __inline__ __attribute__((always_inline)) void drmp3_cpuid(int CPUInfo[], const int InfoType) 620 { 621 #if defined(__PIC__) 622 __asm__ __volatile__( 623 #if defined(__x86_64__) 624 "push %%rbx\n" 625 "cpuid\n" 626 "xchgl %%ebx, %1\n" 627 "pop %%rbx\n" 628 #else 629 "xchgl %%ebx, %1\n" 630 "cpuid\n" 631 "xchgl %%ebx, %1\n" 632 #endif 633 : "=a" (CPUInfo[0]), "=r" (CPUInfo[1]), "=c" (CPUInfo[2]), "=d" (CPUInfo[3]) 634 : "a" (InfoType)); 635 #else 636 __asm__ __volatile__( 637 "cpuid" 638 : "=a" (CPUInfo[0]), "=b" (CPUInfo[1]), "=c" (CPUInfo[2]), "=d" (CPUInfo[3]) 639 : "a" (InfoType)); 640 #endif 641 } 642 #endif 643 static int drmp3_have_simd(void) 644 { 645 #ifdef DR_MP3_ONLY_SIMD 646 return 1; 647 #else 648 static int g_have_simd; 649 int CPUInfo[4]; 650 #ifdef MINIMP3_TEST 651 static int g_counter; 652 if (g_counter++ > 100) 653 return 0; 654 #endif 655 if (g_have_simd) 656 goto end; 657 drmp3_cpuid(CPUInfo, 0); 658 if (CPUInfo[0] > 0) 659 { 660 drmp3_cpuid(CPUInfo, 1); 661 g_have_simd = (CPUInfo[3] & (1 << 26)) + 1; /* SSE2 */ 662 return g_have_simd - 1; 663 } 664 665 end: 666 return g_have_simd - 1; 667 #endif 668 } 669 #elif defined(__ARM_NEON) || defined(__aarch64__) || defined(_M_ARM64) 670 #include <arm_neon.h> 671 #define DRMP3_HAVE_SSE 0 672 #define DRMP3_HAVE_SIMD 1 673 #define DRMP3_VSTORE vst1q_f32 674 #define DRMP3_VLD vld1q_f32 675 #define DRMP3_VSET vmovq_n_f32 676 #define DRMP3_VADD vaddq_f32 677 #define DRMP3_VSUB vsubq_f32 678 #define DRMP3_VMUL vmulq_f32 679 #define DRMP3_VMAC(a, x, y) vmlaq_f32(a, x, y) 680 #define DRMP3_VMSB(a, x, y) vmlsq_f32(a, x, y) 681 #define DRMP3_VMUL_S(x, s) vmulq_f32(x, vmovq_n_f32(s)) 682 #define DRMP3_VREV(x) vcombine_f32(vget_high_f32(vrev64q_f32(x)), vget_low_f32(vrev64q_f32(x))) 683 typedef float32x4_t drmp3_f4; 684 static int drmp3_have_simd(void) 685 { /* TODO: detect neon for !DR_MP3_ONLY_SIMD */ 686 return 1; 687 } 688 #else 689 #define DRMP3_HAVE_SSE 0 690 #define DRMP3_HAVE_SIMD 0 691 #ifdef DR_MP3_ONLY_SIMD 692 #error DR_MP3_ONLY_SIMD used, but SSE/NEON not enabled 693 #endif 694 #endif 695 696 #else 697 698 #define DRMP3_HAVE_SIMD 0 699 700 #endif 701 702 #if defined(__ARM_ARCH) && (__ARM_ARCH >= 6) && !defined(__aarch64__) && !defined(_M_ARM64) 703 #define DRMP3_HAVE_ARMV6 1 704 static __inline__ __attribute__((always_inline)) drmp3_int32 drmp3_clip_int16_arm(drmp3_int32 a) 705 { 706 drmp3_int32 x = 0; 707 __asm__ ("ssat %0, #16, %1" : "=r"(x) : "r"(a)); 708 return x; 709 } 710 #else 711 #define DRMP3_HAVE_ARMV6 0 712 #endif 713 714 715 /* Standard library stuff. */ 716 #ifndef DRMP3_ASSERT 717 #include <assert.h> 718 #define DRMP3_ASSERT(expression) assert(expression) 719 #endif 720 #ifndef DRMP3_COPY_MEMORY 721 #define DRMP3_COPY_MEMORY(dst, src, sz) memcpy((dst), (src), (sz)) 722 #endif 723 #ifndef DRMP3_MOVE_MEMORY 724 #define DRMP3_MOVE_MEMORY(dst, src, sz) memmove((dst), (src), (sz)) 725 #endif 726 #ifndef DRMP3_ZERO_MEMORY 727 #define DRMP3_ZERO_MEMORY(p, sz) memset((p), 0, (sz)) 728 #endif 729 #define DRMP3_ZERO_OBJECT(p) DRMP3_ZERO_MEMORY((p), sizeof(*(p))) 730 #ifndef DRMP3_MALLOC 731 #define DRMP3_MALLOC(sz) malloc((sz)) 732 #endif 733 #ifndef DRMP3_REALLOC 734 #define DRMP3_REALLOC(p, sz) realloc((p), (sz)) 735 #endif 736 #ifndef DRMP3_FREE 737 #define DRMP3_FREE(p) free((p)) 738 #endif 739 740 typedef struct 741 { 742 const drmp3_uint8 *buf; 743 int pos, limit; 744 } drmp3_bs; 745 746 typedef struct 747 { 748 float scf[3*64]; 749 drmp3_uint8 total_bands, stereo_bands, bitalloc[64], scfcod[64]; 750 } drmp3_L12_scale_info; 751 752 typedef struct 753 { 754 drmp3_uint8 tab_offset, code_tab_width, band_count; 755 } drmp3_L12_subband_alloc; 756 757 typedef struct 758 { 759 const drmp3_uint8 *sfbtab; 760 drmp3_uint16 part_23_length, big_values, scalefac_compress; 761 drmp3_uint8 global_gain, block_type, mixed_block_flag, n_long_sfb, n_short_sfb; 762 drmp3_uint8 table_select[3], region_count[3], subblock_gain[3]; 763 drmp3_uint8 preflag, scalefac_scale, count1_table, scfsi; 764 } drmp3_L3_gr_info; 765 766 typedef struct 767 { 768 drmp3_bs bs; 769 drmp3_uint8 maindata[DRMP3_MAX_BITRESERVOIR_BYTES + DRMP3_MAX_L3_FRAME_PAYLOAD_BYTES]; 770 drmp3_L3_gr_info gr_info[4]; 771 float grbuf[2][576], scf[40], syn[18 + 15][2*32]; 772 drmp3_uint8 ist_pos[2][39]; 773 } drmp3dec_scratch; 774 775 static void drmp3_bs_init(drmp3_bs *bs, const drmp3_uint8 *data, int bytes) 776 { 777 bs->buf = data; 778 bs->pos = 0; 779 bs->limit = bytes*8; 780 } 781 782 static drmp3_uint32 drmp3_bs_get_bits(drmp3_bs *bs, int n) 783 { 784 drmp3_uint32 next, cache = 0, s = bs->pos & 7; 785 int shl = n + s; 786 const drmp3_uint8 *p = bs->buf + (bs->pos >> 3); 787 if ((bs->pos += n) > bs->limit) 788 return 0; 789 next = *p++ & (255 >> s); 790 while ((shl -= 8) > 0) 791 { 792 cache |= next << shl; 793 next = *p++; 794 } 795 return cache | (next >> -shl); 796 } 797 798 static int drmp3_hdr_valid(const drmp3_uint8 *h) 799 { 800 return h[0] == 0xff && 801 ((h[1] & 0xF0) == 0xf0 || (h[1] & 0xFE) == 0xe2) && 802 (DRMP3_HDR_GET_LAYER(h) != 0) && 803 (DRMP3_HDR_GET_BITRATE(h) != 15) && 804 (DRMP3_HDR_GET_SAMPLE_RATE(h) != 3); 805 } 806 807 static int drmp3_hdr_compare(const drmp3_uint8 *h1, const drmp3_uint8 *h2) 808 { 809 return drmp3_hdr_valid(h2) && 810 ((h1[1] ^ h2[1]) & 0xFE) == 0 && 811 ((h1[2] ^ h2[2]) & 0x0C) == 0 && 812 !(DRMP3_HDR_IS_FREE_FORMAT(h1) ^ DRMP3_HDR_IS_FREE_FORMAT(h2)); 813 } 814 815 static unsigned drmp3_hdr_bitrate_kbps(const drmp3_uint8 *h) 816 { 817 static const drmp3_uint8 halfrate[2][3][15] = { 818 { { 0,4,8,12,16,20,24,28,32,40,48,56,64,72,80 }, { 0,4,8,12,16,20,24,28,32,40,48,56,64,72,80 }, { 0,16,24,28,32,40,48,56,64,72,80,88,96,112,128 } }, 819 { { 0,16,20,24,28,32,40,48,56,64,80,96,112,128,160 }, { 0,16,24,28,32,40,48,56,64,80,96,112,128,160,192 }, { 0,16,32,48,64,80,96,112,128,144,160,176,192,208,224 } }, 820 }; 821 return 2*halfrate[!!DRMP3_HDR_TEST_MPEG1(h)][DRMP3_HDR_GET_LAYER(h) - 1][DRMP3_HDR_GET_BITRATE(h)]; 822 } 823 824 static unsigned drmp3_hdr_sample_rate_hz(const drmp3_uint8 *h) 825 { 826 static const unsigned g_hz[3] = { 44100, 48000, 32000 }; 827 return g_hz[DRMP3_HDR_GET_SAMPLE_RATE(h)] >> (int)!DRMP3_HDR_TEST_MPEG1(h) >> (int)!DRMP3_HDR_TEST_NOT_MPEG25(h); 828 } 829 830 static unsigned drmp3_hdr_frame_samples(const drmp3_uint8 *h) 831 { 832 return DRMP3_HDR_IS_LAYER_1(h) ? 384 : (1152 >> (int)DRMP3_HDR_IS_FRAME_576(h)); 833 } 834 835 static int drmp3_hdr_frame_bytes(const drmp3_uint8 *h, int free_format_size) 836 { 837 int frame_bytes = drmp3_hdr_frame_samples(h)*drmp3_hdr_bitrate_kbps(h)*125/drmp3_hdr_sample_rate_hz(h); 838 if (DRMP3_HDR_IS_LAYER_1(h)) 839 { 840 frame_bytes &= ~3; /* slot align */ 841 } 842 return frame_bytes ? frame_bytes : free_format_size; 843 } 844 845 static int drmp3_hdr_padding(const drmp3_uint8 *h) 846 { 847 return DRMP3_HDR_TEST_PADDING(h) ? (DRMP3_HDR_IS_LAYER_1(h) ? 4 : 1) : 0; 848 } 849 850 #ifndef DR_MP3_ONLY_MP3 851 static const drmp3_L12_subband_alloc *drmp3_L12_subband_alloc_table(const drmp3_uint8 *hdr, drmp3_L12_scale_info *sci) 852 { 853 const drmp3_L12_subband_alloc *alloc; 854 int mode = DRMP3_HDR_GET_STEREO_MODE(hdr); 855 int nbands, stereo_bands = (mode == DRMP3_MODE_MONO) ? 0 : (mode == DRMP3_MODE_JOINT_STEREO) ? (DRMP3_HDR_GET_STEREO_MODE_EXT(hdr) << 2) + 4 : 32; 856 857 if (DRMP3_HDR_IS_LAYER_1(hdr)) 858 { 859 static const drmp3_L12_subband_alloc g_alloc_L1[] = { { 76, 4, 32 } }; 860 alloc = g_alloc_L1; 861 nbands = 32; 862 } else if (!DRMP3_HDR_TEST_MPEG1(hdr)) 863 { 864 static const drmp3_L12_subband_alloc g_alloc_L2M2[] = { { 60, 4, 4 }, { 44, 3, 7 }, { 44, 2, 19 } }; 865 alloc = g_alloc_L2M2; 866 nbands = 30; 867 } else 868 { 869 static const drmp3_L12_subband_alloc g_alloc_L2M1[] = { { 0, 4, 3 }, { 16, 4, 8 }, { 32, 3, 12 }, { 40, 2, 7 } }; 870 int sample_rate_idx = DRMP3_HDR_GET_SAMPLE_RATE(hdr); 871 unsigned kbps = drmp3_hdr_bitrate_kbps(hdr) >> (int)(mode != DRMP3_MODE_MONO); 872 if (!kbps) /* free-format */ 873 { 874 kbps = 192; 875 } 876 877 alloc = g_alloc_L2M1; 878 nbands = 27; 879 if (kbps < 56) 880 { 881 static const drmp3_L12_subband_alloc g_alloc_L2M1_lowrate[] = { { 44, 4, 2 }, { 44, 3, 10 } }; 882 alloc = g_alloc_L2M1_lowrate; 883 nbands = sample_rate_idx == 2 ? 12 : 8; 884 } else if (kbps >= 96 && sample_rate_idx != 1) 885 { 886 nbands = 30; 887 } 888 } 889 890 sci->total_bands = (drmp3_uint8)nbands; 891 sci->stereo_bands = (drmp3_uint8)DRMP3_MIN(stereo_bands, nbands); 892 893 return alloc; 894 } 895 896 static void drmp3_L12_read_scalefactors(drmp3_bs *bs, drmp3_uint8 *pba, drmp3_uint8 *scfcod, int bands, float *scf) 897 { 898 static const float g_deq_L12[18*3] = { 899 #define DRMP3_DQ(x) 9.53674316e-07f/x, 7.56931807e-07f/x, 6.00777173e-07f/x 900 DRMP3_DQ(3),DRMP3_DQ(7),DRMP3_DQ(15),DRMP3_DQ(31),DRMP3_DQ(63),DRMP3_DQ(127),DRMP3_DQ(255),DRMP3_DQ(511),DRMP3_DQ(1023),DRMP3_DQ(2047),DRMP3_DQ(4095),DRMP3_DQ(8191),DRMP3_DQ(16383),DRMP3_DQ(32767),DRMP3_DQ(65535),DRMP3_DQ(3),DRMP3_DQ(5),DRMP3_DQ(9) 901 }; 902 int i, m; 903 for (i = 0; i < bands; i++) 904 { 905 float s = 0; 906 int ba = *pba++; 907 int mask = ba ? 4 + ((19 >> scfcod[i]) & 3) : 0; 908 for (m = 4; m; m >>= 1) 909 { 910 if (mask & m) 911 { 912 int b = drmp3_bs_get_bits(bs, 6); 913 s = g_deq_L12[ba*3 - 6 + b % 3]*(int)(1 << 21 >> b/3); 914 } 915 *scf++ = s; 916 } 917 } 918 } 919 920 static void drmp3_L12_read_scale_info(const drmp3_uint8 *hdr, drmp3_bs *bs, drmp3_L12_scale_info *sci) 921 { 922 static const drmp3_uint8 g_bitalloc_code_tab[] = { 923 0,17, 3, 4, 5,6,7, 8,9,10,11,12,13,14,15,16, 924 0,17,18, 3,19,4,5, 6,7, 8, 9,10,11,12,13,16, 925 0,17,18, 3,19,4,5,16, 926 0,17,18,16, 927 0,17,18,19, 4,5,6, 7,8, 9,10,11,12,13,14,15, 928 0,17,18, 3,19,4,5, 6,7, 8, 9,10,11,12,13,14, 929 0, 2, 3, 4, 5,6,7, 8,9,10,11,12,13,14,15,16 930 }; 931 const drmp3_L12_subband_alloc *subband_alloc = drmp3_L12_subband_alloc_table(hdr, sci); 932 933 int i, k = 0, ba_bits = 0; 934 const drmp3_uint8 *ba_code_tab = g_bitalloc_code_tab; 935 936 for (i = 0; i < sci->total_bands; i++) 937 { 938 drmp3_uint8 ba; 939 if (i == k) 940 { 941 k += subband_alloc->band_count; 942 ba_bits = subband_alloc->code_tab_width; 943 ba_code_tab = g_bitalloc_code_tab + subband_alloc->tab_offset; 944 subband_alloc++; 945 } 946 ba = ba_code_tab[drmp3_bs_get_bits(bs, ba_bits)]; 947 sci->bitalloc[2*i] = ba; 948 if (i < sci->stereo_bands) 949 { 950 ba = ba_code_tab[drmp3_bs_get_bits(bs, ba_bits)]; 951 } 952 sci->bitalloc[2*i + 1] = sci->stereo_bands ? ba : 0; 953 } 954 955 for (i = 0; i < 2*sci->total_bands; i++) 956 { 957 sci->scfcod[i] = (drmp3_uint8)(sci->bitalloc[i] ? DRMP3_HDR_IS_LAYER_1(hdr) ? 2 : drmp3_bs_get_bits(bs, 2) : 6); 958 } 959 960 drmp3_L12_read_scalefactors(bs, sci->bitalloc, sci->scfcod, sci->total_bands*2, sci->scf); 961 962 for (i = sci->stereo_bands; i < sci->total_bands; i++) 963 { 964 sci->bitalloc[2*i + 1] = 0; 965 } 966 } 967 968 static int drmp3_L12_dequantize_granule(float *grbuf, drmp3_bs *bs, drmp3_L12_scale_info *sci, int group_size) 969 { 970 int i, j, k, choff = 576; 971 for (j = 0; j < 4; j++) 972 { 973 float *dst = grbuf + group_size*j; 974 for (i = 0; i < 2*sci->total_bands; i++) 975 { 976 int ba = sci->bitalloc[i]; 977 if (ba != 0) 978 { 979 if (ba < 17) 980 { 981 int half = (1 << (ba - 1)) - 1; 982 for (k = 0; k < group_size; k++) 983 { 984 dst[k] = (float)((int)drmp3_bs_get_bits(bs, ba) - half); 985 } 986 } else 987 { 988 unsigned mod = (2 << (ba - 17)) + 1; /* 3, 5, 9 */ 989 unsigned code = drmp3_bs_get_bits(bs, mod + 2 - (mod >> 3)); /* 5, 7, 10 */ 990 for (k = 0; k < group_size; k++, code /= mod) 991 { 992 dst[k] = (float)((int)(code % mod - mod/2)); 993 } 994 } 995 } 996 dst += choff; 997 choff = 18 - choff; 998 } 999 } 1000 return group_size*4; 1001 } 1002 1003 static void drmp3_L12_apply_scf_384(drmp3_L12_scale_info *sci, const float *scf, float *dst) 1004 { 1005 int i, k; 1006 DRMP3_COPY_MEMORY(dst + 576 + sci->stereo_bands*18, dst + sci->stereo_bands*18, (sci->total_bands - sci->stereo_bands)*18*sizeof(float)); 1007 for (i = 0; i < sci->total_bands; i++, dst += 18, scf += 6) 1008 { 1009 for (k = 0; k < 12; k++) 1010 { 1011 dst[k + 0] *= scf[0]; 1012 dst[k + 576] *= scf[3]; 1013 } 1014 } 1015 } 1016 #endif 1017 1018 static int drmp3_L3_read_side_info(drmp3_bs *bs, drmp3_L3_gr_info *gr, const drmp3_uint8 *hdr) 1019 { 1020 static const drmp3_uint8 g_scf_long[8][23] = { 1021 { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, 1022 { 12,12,12,12,12,12,16,20,24,28,32,40,48,56,64,76,90,2,2,2,2,2,0 }, 1023 { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, 1024 { 6,6,6,6,6,6,8,10,12,14,16,18,22,26,32,38,46,54,62,70,76,36,0 }, 1025 { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, 1026 { 4,4,4,4,4,4,6,6,8,8,10,12,16,20,24,28,34,42,50,54,76,158,0 }, 1027 { 4,4,4,4,4,4,6,6,6,8,10,12,16,18,22,28,34,40,46,54,54,192,0 }, 1028 { 4,4,4,4,4,4,6,6,8,10,12,16,20,24,30,38,46,56,68,84,102,26,0 } 1029 }; 1030 static const drmp3_uint8 g_scf_short[8][40] = { 1031 { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, 1032 { 8,8,8,8,8,8,8,8,8,12,12,12,16,16,16,20,20,20,24,24,24,28,28,28,36,36,36,2,2,2,2,2,2,2,2,2,26,26,26,0 }, 1033 { 4,4,4,4,4,4,4,4,4,6,6,6,6,6,6,8,8,8,10,10,10,14,14,14,18,18,18,26,26,26,32,32,32,42,42,42,18,18,18,0 }, 1034 { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,32,32,32,44,44,44,12,12,12,0 }, 1035 { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, 1036 { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,22,22,22,30,30,30,56,56,56,0 }, 1037 { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,6,6,6,10,10,10,12,12,12,14,14,14,16,16,16,20,20,20,26,26,26,66,66,66,0 }, 1038 { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,12,12,12,16,16,16,20,20,20,26,26,26,34,34,34,42,42,42,12,12,12,0 } 1039 }; 1040 static const drmp3_uint8 g_scf_mixed[8][40] = { 1041 { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, 1042 { 12,12,12,4,4,4,8,8,8,12,12,12,16,16,16,20,20,20,24,24,24,28,28,28,36,36,36,2,2,2,2,2,2,2,2,2,26,26,26,0 }, 1043 { 6,6,6,6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,14,14,14,18,18,18,26,26,26,32,32,32,42,42,42,18,18,18,0 }, 1044 { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,32,32,32,44,44,44,12,12,12,0 }, 1045 { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, 1046 { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,22,22,22,30,30,30,56,56,56,0 }, 1047 { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,6,6,6,10,10,10,12,12,12,14,14,14,16,16,16,20,20,20,26,26,26,66,66,66,0 }, 1048 { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,8,8,8,12,12,12,16,16,16,20,20,20,26,26,26,34,34,34,42,42,42,12,12,12,0 } 1049 }; 1050 1051 unsigned tables, scfsi = 0; 1052 int main_data_begin, part_23_sum = 0; 1053 int gr_count = DRMP3_HDR_IS_MONO(hdr) ? 1 : 2; 1054 int sr_idx = DRMP3_HDR_GET_MY_SAMPLE_RATE(hdr); sr_idx -= (sr_idx != 0); 1055 1056 if (DRMP3_HDR_TEST_MPEG1(hdr)) 1057 { 1058 gr_count *= 2; 1059 main_data_begin = drmp3_bs_get_bits(bs, 9); 1060 scfsi = drmp3_bs_get_bits(bs, 7 + gr_count); 1061 } else 1062 { 1063 main_data_begin = drmp3_bs_get_bits(bs, 8 + gr_count) >> gr_count; 1064 } 1065 1066 do 1067 { 1068 if (DRMP3_HDR_IS_MONO(hdr)) 1069 { 1070 scfsi <<= 4; 1071 } 1072 gr->part_23_length = (drmp3_uint16)drmp3_bs_get_bits(bs, 12); 1073 part_23_sum += gr->part_23_length; 1074 gr->big_values = (drmp3_uint16)drmp3_bs_get_bits(bs, 9); 1075 if (gr->big_values > 288) 1076 { 1077 return -1; 1078 } 1079 gr->global_gain = (drmp3_uint8)drmp3_bs_get_bits(bs, 8); 1080 gr->scalefac_compress = (drmp3_uint16)drmp3_bs_get_bits(bs, DRMP3_HDR_TEST_MPEG1(hdr) ? 4 : 9); 1081 gr->sfbtab = g_scf_long[sr_idx]; 1082 gr->n_long_sfb = 22; 1083 gr->n_short_sfb = 0; 1084 if (drmp3_bs_get_bits(bs, 1)) 1085 { 1086 gr->block_type = (drmp3_uint8)drmp3_bs_get_bits(bs, 2); 1087 if (!gr->block_type) 1088 { 1089 return -1; 1090 } 1091 gr->mixed_block_flag = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); 1092 gr->region_count[0] = 7; 1093 gr->region_count[1] = 255; 1094 if (gr->block_type == DRMP3_SHORT_BLOCK_TYPE) 1095 { 1096 scfsi &= 0x0F0F; 1097 if (!gr->mixed_block_flag) 1098 { 1099 gr->region_count[0] = 8; 1100 gr->sfbtab = g_scf_short[sr_idx]; 1101 gr->n_long_sfb = 0; 1102 gr->n_short_sfb = 39; 1103 } else 1104 { 1105 gr->sfbtab = g_scf_mixed[sr_idx]; 1106 gr->n_long_sfb = DRMP3_HDR_TEST_MPEG1(hdr) ? 8 : 6; 1107 gr->n_short_sfb = 30; 1108 } 1109 } 1110 tables = drmp3_bs_get_bits(bs, 10); 1111 tables <<= 5; 1112 gr->subblock_gain[0] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); 1113 gr->subblock_gain[1] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); 1114 gr->subblock_gain[2] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); 1115 } else 1116 { 1117 gr->block_type = 0; 1118 gr->mixed_block_flag = 0; 1119 tables = drmp3_bs_get_bits(bs, 15); 1120 gr->region_count[0] = (drmp3_uint8)drmp3_bs_get_bits(bs, 4); 1121 gr->region_count[1] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); 1122 gr->region_count[2] = 255; 1123 } 1124 gr->table_select[0] = (drmp3_uint8)(tables >> 10); 1125 gr->table_select[1] = (drmp3_uint8)((tables >> 5) & 31); 1126 gr->table_select[2] = (drmp3_uint8)((tables) & 31); 1127 gr->preflag = (drmp3_uint8)(DRMP3_HDR_TEST_MPEG1(hdr) ? drmp3_bs_get_bits(bs, 1) : (gr->scalefac_compress >= 500)); 1128 gr->scalefac_scale = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); 1129 gr->count1_table = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); 1130 gr->scfsi = (drmp3_uint8)((scfsi >> 12) & 15); 1131 scfsi <<= 4; 1132 gr++; 1133 } while(--gr_count); 1134 1135 if (part_23_sum + bs->pos > bs->limit + main_data_begin*8) 1136 { 1137 return -1; 1138 } 1139 1140 return main_data_begin; 1141 } 1142 1143 static void drmp3_L3_read_scalefactors(drmp3_uint8 *scf, drmp3_uint8 *ist_pos, const drmp3_uint8 *scf_size, const drmp3_uint8 *scf_count, drmp3_bs *bitbuf, int scfsi) 1144 { 1145 int i, k; 1146 for (i = 0; i < 4 && scf_count[i]; i++, scfsi *= 2) 1147 { 1148 int cnt = scf_count[i]; 1149 if (scfsi & 8) 1150 { 1151 DRMP3_COPY_MEMORY(scf, ist_pos, cnt); 1152 } else 1153 { 1154 int bits = scf_size[i]; 1155 if (!bits) 1156 { 1157 DRMP3_ZERO_MEMORY(scf, cnt); 1158 DRMP3_ZERO_MEMORY(ist_pos, cnt); 1159 } else 1160 { 1161 int max_scf = (scfsi < 0) ? (1 << bits) - 1 : -1; 1162 for (k = 0; k < cnt; k++) 1163 { 1164 int s = drmp3_bs_get_bits(bitbuf, bits); 1165 ist_pos[k] = (drmp3_uint8)(s == max_scf ? -1 : s); 1166 scf[k] = (drmp3_uint8)s; 1167 } 1168 } 1169 } 1170 ist_pos += cnt; 1171 scf += cnt; 1172 } 1173 scf[0] = scf[1] = scf[2] = 0; 1174 } 1175 1176 static float drmp3_L3_ldexp_q2(float y, int exp_q2) 1177 { 1178 static const float g_expfrac[4] = { 9.31322575e-10f,7.83145814e-10f,6.58544508e-10f,5.53767716e-10f }; 1179 int e; 1180 do 1181 { 1182 e = DRMP3_MIN(30*4, exp_q2); 1183 y *= g_expfrac[e & 3]*(1 << 30 >> (e >> 2)); 1184 } while ((exp_q2 -= e) > 0); 1185 return y; 1186 } 1187 1188 static void drmp3_L3_decode_scalefactors(const drmp3_uint8 *hdr, drmp3_uint8 *ist_pos, drmp3_bs *bs, const drmp3_L3_gr_info *gr, float *scf, int ch) 1189 { 1190 static const drmp3_uint8 g_scf_partitions[3][28] = { 1191 { 6,5,5, 5,6,5,5,5,6,5, 7,3,11,10,0,0, 7, 7, 7,0, 6, 6,6,3, 8, 8,5,0 }, 1192 { 8,9,6,12,6,9,9,9,6,9,12,6,15,18,0,0, 6,15,12,0, 6,12,9,6, 6,18,9,0 }, 1193 { 9,9,6,12,9,9,9,9,9,9,12,6,18,18,0,0,12,12,12,0,12, 9,9,6,15,12,9,0 } 1194 }; 1195 const drmp3_uint8 *scf_partition = g_scf_partitions[!!gr->n_short_sfb + !gr->n_long_sfb]; 1196 drmp3_uint8 scf_size[4], iscf[40]; 1197 int i, scf_shift = gr->scalefac_scale + 1, gain_exp, scfsi = gr->scfsi; 1198 float gain; 1199 1200 if (DRMP3_HDR_TEST_MPEG1(hdr)) 1201 { 1202 static const drmp3_uint8 g_scfc_decode[16] = { 0,1,2,3, 12,5,6,7, 9,10,11,13, 14,15,18,19 }; 1203 int part = g_scfc_decode[gr->scalefac_compress]; 1204 scf_size[1] = scf_size[0] = (drmp3_uint8)(part >> 2); 1205 scf_size[3] = scf_size[2] = (drmp3_uint8)(part & 3); 1206 } else 1207 { 1208 static const drmp3_uint8 g_mod[6*4] = { 5,5,4,4,5,5,4,1,4,3,1,1,5,6,6,1,4,4,4,1,4,3,1,1 }; 1209 int k, modprod, sfc, ist = DRMP3_HDR_TEST_I_STEREO(hdr) && ch; 1210 sfc = gr->scalefac_compress >> ist; 1211 for (k = ist*3*4; sfc >= 0; sfc -= modprod, k += 4) 1212 { 1213 for (modprod = 1, i = 3; i >= 0; i--) 1214 { 1215 scf_size[i] = (drmp3_uint8)(sfc / modprod % g_mod[k + i]); 1216 modprod *= g_mod[k + i]; 1217 } 1218 } 1219 scf_partition += k; 1220 scfsi = -16; 1221 } 1222 drmp3_L3_read_scalefactors(iscf, ist_pos, scf_size, scf_partition, bs, scfsi); 1223 1224 if (gr->n_short_sfb) 1225 { 1226 int sh = 3 - scf_shift; 1227 for (i = 0; i < gr->n_short_sfb; i += 3) 1228 { 1229 iscf[gr->n_long_sfb + i + 0] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 0] + (gr->subblock_gain[0] << sh)); 1230 iscf[gr->n_long_sfb + i + 1] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 1] + (gr->subblock_gain[1] << sh)); 1231 iscf[gr->n_long_sfb + i + 2] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 2] + (gr->subblock_gain[2] << sh)); 1232 } 1233 } else if (gr->preflag) 1234 { 1235 static const drmp3_uint8 g_preamp[10] = { 1,1,1,1,2,2,3,3,3,2 }; 1236 for (i = 0; i < 10; i++) 1237 { 1238 iscf[11 + i] = (drmp3_uint8)(iscf[11 + i] + g_preamp[i]); 1239 } 1240 } 1241 1242 gain_exp = gr->global_gain + DRMP3_BITS_DEQUANTIZER_OUT*4 - 210 - (DRMP3_HDR_IS_MS_STEREO(hdr) ? 2 : 0); 1243 gain = drmp3_L3_ldexp_q2(1 << (DRMP3_MAX_SCFI/4), DRMP3_MAX_SCFI - gain_exp); 1244 for (i = 0; i < (int)(gr->n_long_sfb + gr->n_short_sfb); i++) 1245 { 1246 scf[i] = drmp3_L3_ldexp_q2(gain, iscf[i] << scf_shift); 1247 } 1248 } 1249 1250 static const float g_drmp3_pow43[129 + 16] = { 1251 0,-1,-2.519842f,-4.326749f,-6.349604f,-8.549880f,-10.902724f,-13.390518f,-16.000000f,-18.720754f,-21.544347f,-24.463781f,-27.473142f,-30.567351f,-33.741992f,-36.993181f, 1252 0,1,2.519842f,4.326749f,6.349604f,8.549880f,10.902724f,13.390518f,16.000000f,18.720754f,21.544347f,24.463781f,27.473142f,30.567351f,33.741992f,36.993181f,40.317474f,43.711787f,47.173345f,50.699631f,54.288352f,57.937408f,61.644865f,65.408941f,69.227979f,73.100443f,77.024898f,81.000000f,85.024491f,89.097188f,93.216975f,97.382800f,101.593667f,105.848633f,110.146801f,114.487321f,118.869381f,123.292209f,127.755065f,132.257246f,136.798076f,141.376907f,145.993119f,150.646117f,155.335327f,160.060199f,164.820202f,169.614826f,174.443577f,179.305980f,184.201575f,189.129918f,194.090580f,199.083145f,204.107210f,209.162385f,214.248292f,219.364564f,224.510845f,229.686789f,234.892058f,240.126328f,245.389280f,250.680604f,256.000000f,261.347174f,266.721841f,272.123723f,277.552547f,283.008049f,288.489971f,293.998060f,299.532071f,305.091761f,310.676898f,316.287249f,321.922592f,327.582707f,333.267377f,338.976394f,344.709550f,350.466646f,356.247482f,362.051866f,367.879608f,373.730522f,379.604427f,385.501143f,391.420496f,397.362314f,403.326427f,409.312672f,415.320884f,421.350905f,427.402579f,433.475750f,439.570269f,445.685987f,451.822757f,457.980436f,464.158883f,470.357960f,476.577530f,482.817459f,489.077615f,495.357868f,501.658090f,507.978156f,514.317941f,520.677324f,527.056184f,533.454404f,539.871867f,546.308458f,552.764065f,559.238575f,565.731879f,572.243870f,578.774440f,585.323483f,591.890898f,598.476581f,605.080431f,611.702349f,618.342238f,625.000000f,631.675540f,638.368763f,645.079578f 1253 }; 1254 1255 static float drmp3_L3_pow_43(int x) 1256 { 1257 float frac; 1258 int sign, mult = 256; 1259 1260 if (x < 129) 1261 { 1262 return g_drmp3_pow43[16 + x]; 1263 } 1264 1265 if (x < 1024) 1266 { 1267 mult = 16; 1268 x <<= 3; 1269 } 1270 1271 sign = 2*x & 64; 1272 frac = (float)((x & 63) - sign) / ((x & ~63) + sign); 1273 return g_drmp3_pow43[16 + ((x + sign) >> 6)]*(1.f + frac*((4.f/3) + frac*(2.f/9)))*mult; 1274 } 1275 1276 static void drmp3_L3_huffman(float *dst, drmp3_bs *bs, const drmp3_L3_gr_info *gr_info, const float *scf, int layer3gr_limit) 1277 { 1278 static const drmp3_int16 tabs[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1279 785,785,785,785,784,784,784,784,513,513,513,513,513,513,513,513,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256, 1280 -255,1313,1298,1282,785,785,785,785,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,290,288, 1281 -255,1313,1298,1282,769,769,769,769,529,529,529,529,529,529,529,529,528,528,528,528,528,528,528,528,512,512,512,512,512,512,512,512,290,288, 1282 -253,-318,-351,-367,785,785,785,785,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,819,818,547,547,275,275,275,275,561,560,515,546,289,274,288,258, 1283 -254,-287,1329,1299,1314,1312,1057,1057,1042,1042,1026,1026,784,784,784,784,529,529,529,529,529,529,529,529,769,769,769,769,768,768,768,768,563,560,306,306,291,259, 1284 -252,-413,-477,-542,1298,-575,1041,1041,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-383,-399,1107,1092,1106,1061,849,849,789,789,1104,1091,773,773,1076,1075,341,340,325,309,834,804,577,577,532,532,516,516,832,818,803,816,561,561,531,531,515,546,289,289,288,258, 1285 -252,-429,-493,-559,1057,1057,1042,1042,529,529,529,529,529,529,529,529,784,784,784,784,769,769,769,769,512,512,512,512,512,512,512,512,-382,1077,-415,1106,1061,1104,849,849,789,789,1091,1076,1029,1075,834,834,597,581,340,340,339,324,804,833,532,532,832,772,818,803,817,787,816,771,290,290,290,290,288,258, 1286 -253,-349,-414,-447,-463,1329,1299,-479,1314,1312,1057,1057,1042,1042,1026,1026,785,785,785,785,784,784,784,784,769,769,769,769,768,768,768,768,-319,851,821,-335,836,850,805,849,341,340,325,336,533,533,579,579,564,564,773,832,578,548,563,516,321,276,306,291,304,259, 1287 -251,-572,-733,-830,-863,-879,1041,1041,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-511,-527,-543,1396,1351,1381,1366,1395,1335,1380,-559,1334,1138,1138,1063,1063,1350,1392,1031,1031,1062,1062,1364,1363,1120,1120,1333,1348,881,881,881,881,375,374,359,373,343,358,341,325,791,791,1123,1122,-703,1105,1045,-719,865,865,790,790,774,774,1104,1029,338,293,323,308,-799,-815,833,788,772,818,803,816,322,292,307,320,561,531,515,546,289,274,288,258, 1288 -251,-525,-605,-685,-765,-831,-846,1298,1057,1057,1312,1282,785,785,785,785,784,784,784,784,769,769,769,769,512,512,512,512,512,512,512,512,1399,1398,1383,1367,1382,1396,1351,-511,1381,1366,1139,1139,1079,1079,1124,1124,1364,1349,1363,1333,882,882,882,882,807,807,807,807,1094,1094,1136,1136,373,341,535,535,881,775,867,822,774,-591,324,338,-671,849,550,550,866,864,609,609,293,336,534,534,789,835,773,-751,834,804,308,307,833,788,832,772,562,562,547,547,305,275,560,515,290,290, 1289 -252,-397,-477,-557,-622,-653,-719,-735,-750,1329,1299,1314,1057,1057,1042,1042,1312,1282,1024,1024,785,785,785,785,784,784,784,784,769,769,769,769,-383,1127,1141,1111,1126,1140,1095,1110,869,869,883,883,1079,1109,882,882,375,374,807,868,838,881,791,-463,867,822,368,263,852,837,836,-543,610,610,550,550,352,336,534,534,865,774,851,821,850,805,593,533,579,564,773,832,578,578,548,548,577,577,307,276,306,291,516,560,259,259, 1290 -250,-2107,-2507,-2764,-2909,-2974,-3007,-3023,1041,1041,1040,1040,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-767,-1052,-1213,-1277,-1358,-1405,-1469,-1535,-1550,-1582,-1614,-1647,-1662,-1694,-1726,-1759,-1774,-1807,-1822,-1854,-1886,1565,-1919,-1935,-1951,-1967,1731,1730,1580,1717,-1983,1729,1564,-1999,1548,-2015,-2031,1715,1595,-2047,1714,-2063,1610,-2079,1609,-2095,1323,1323,1457,1457,1307,1307,1712,1547,1641,1700,1699,1594,1685,1625,1442,1442,1322,1322,-780,-973,-910,1279,1278,1277,1262,1276,1261,1275,1215,1260,1229,-959,974,974,989,989,-943,735,478,478,495,463,506,414,-1039,1003,958,1017,927,942,987,957,431,476,1272,1167,1228,-1183,1256,-1199,895,895,941,941,1242,1227,1212,1135,1014,1014,490,489,503,487,910,1013,985,925,863,894,970,955,1012,847,-1343,831,755,755,984,909,428,366,754,559,-1391,752,486,457,924,997,698,698,983,893,740,740,908,877,739,739,667,667,953,938,497,287,271,271,683,606,590,712,726,574,302,302,738,736,481,286,526,725,605,711,636,724,696,651,589,681,666,710,364,467,573,695,466,466,301,465,379,379,709,604,665,679,316,316,634,633,436,436,464,269,424,394,452,332,438,363,347,408,393,448,331,422,362,407,392,421,346,406,391,376,375,359,1441,1306,-2367,1290,-2383,1337,-2399,-2415,1426,1321,-2431,1411,1336,-2447,-2463,-2479,1169,1169,1049,1049,1424,1289,1412,1352,1319,-2495,1154,1154,1064,1064,1153,1153,416,390,360,404,403,389,344,374,373,343,358,372,327,357,342,311,356,326,1395,1394,1137,1137,1047,1047,1365,1392,1287,1379,1334,1364,1349,1378,1318,1363,792,792,792,792,1152,1152,1032,1032,1121,1121,1046,1046,1120,1120,1030,1030,-2895,1106,1061,1104,849,849,789,789,1091,1076,1029,1090,1060,1075,833,833,309,324,532,532,832,772,818,803,561,561,531,560,515,546,289,274,288,258, 1291 -250,-1179,-1579,-1836,-1996,-2124,-2253,-2333,-2413,-2477,-2542,-2574,-2607,-2622,-2655,1314,1313,1298,1312,1282,785,785,785,785,1040,1040,1025,1025,768,768,768,768,-766,-798,-830,-862,-895,-911,-927,-943,-959,-975,-991,-1007,-1023,-1039,-1055,-1070,1724,1647,-1103,-1119,1631,1767,1662,1738,1708,1723,-1135,1780,1615,1779,1599,1677,1646,1778,1583,-1151,1777,1567,1737,1692,1765,1722,1707,1630,1751,1661,1764,1614,1736,1676,1763,1750,1645,1598,1721,1691,1762,1706,1582,1761,1566,-1167,1749,1629,767,766,751,765,494,494,735,764,719,749,734,763,447,447,748,718,477,506,431,491,446,476,461,505,415,430,475,445,504,399,460,489,414,503,383,474,429,459,502,502,746,752,488,398,501,473,413,472,486,271,480,270,-1439,-1455,1357,-1471,-1487,-1503,1341,1325,-1519,1489,1463,1403,1309,-1535,1372,1448,1418,1476,1356,1462,1387,-1551,1475,1340,1447,1402,1386,-1567,1068,1068,1474,1461,455,380,468,440,395,425,410,454,364,467,466,464,453,269,409,448,268,432,1371,1473,1432,1417,1308,1460,1355,1446,1459,1431,1083,1083,1401,1416,1458,1445,1067,1067,1370,1457,1051,1051,1291,1430,1385,1444,1354,1415,1400,1443,1082,1082,1173,1113,1186,1066,1185,1050,-1967,1158,1128,1172,1097,1171,1081,-1983,1157,1112,416,266,375,400,1170,1142,1127,1065,793,793,1169,1033,1156,1096,1141,1111,1155,1080,1126,1140,898,898,808,808,897,897,792,792,1095,1152,1032,1125,1110,1139,1079,1124,882,807,838,881,853,791,-2319,867,368,263,822,852,837,866,806,865,-2399,851,352,262,534,534,821,836,594,594,549,549,593,593,533,533,848,773,579,579,564,578,548,563,276,276,577,576,306,291,516,560,305,305,275,259, 1292 -251,-892,-2058,-2620,-2828,-2957,-3023,-3039,1041,1041,1040,1040,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-511,-527,-543,-559,1530,-575,-591,1528,1527,1407,1526,1391,1023,1023,1023,1023,1525,1375,1268,1268,1103,1103,1087,1087,1039,1039,1523,-604,815,815,815,815,510,495,509,479,508,463,507,447,431,505,415,399,-734,-782,1262,-815,1259,1244,-831,1258,1228,-847,-863,1196,-879,1253,987,987,748,-767,493,493,462,477,414,414,686,669,478,446,461,445,474,429,487,458,412,471,1266,1264,1009,1009,799,799,-1019,-1276,-1452,-1581,-1677,-1757,-1821,-1886,-1933,-1997,1257,1257,1483,1468,1512,1422,1497,1406,1467,1496,1421,1510,1134,1134,1225,1225,1466,1451,1374,1405,1252,1252,1358,1480,1164,1164,1251,1251,1238,1238,1389,1465,-1407,1054,1101,-1423,1207,-1439,830,830,1248,1038,1237,1117,1223,1148,1236,1208,411,426,395,410,379,269,1193,1222,1132,1235,1221,1116,976,976,1192,1162,1177,1220,1131,1191,963,963,-1647,961,780,-1663,558,558,994,993,437,408,393,407,829,978,813,797,947,-1743,721,721,377,392,844,950,828,890,706,706,812,859,796,960,948,843,934,874,571,571,-1919,690,555,689,421,346,539,539,944,779,918,873,932,842,903,888,570,570,931,917,674,674,-2575,1562,-2591,1609,-2607,1654,1322,1322,1441,1441,1696,1546,1683,1593,1669,1624,1426,1426,1321,1321,1639,1680,1425,1425,1305,1305,1545,1668,1608,1623,1667,1592,1638,1666,1320,1320,1652,1607,1409,1409,1304,1304,1288,1288,1664,1637,1395,1395,1335,1335,1622,1636,1394,1394,1319,1319,1606,1621,1392,1392,1137,1137,1137,1137,345,390,360,375,404,373,1047,-2751,-2767,-2783,1062,1121,1046,-2799,1077,-2815,1106,1061,789,789,1105,1104,263,355,310,340,325,354,352,262,339,324,1091,1076,1029,1090,1060,1075,833,833,788,788,1088,1028,818,818,803,803,561,561,531,531,816,771,546,546,289,274,288,258, 1293 -253,-317,-381,-446,-478,-509,1279,1279,-811,-1179,-1451,-1756,-1900,-2028,-2189,-2253,-2333,-2414,-2445,-2511,-2526,1313,1298,-2559,1041,1041,1040,1040,1025,1025,1024,1024,1022,1007,1021,991,1020,975,1019,959,687,687,1018,1017,671,671,655,655,1016,1015,639,639,758,758,623,623,757,607,756,591,755,575,754,559,543,543,1009,783,-575,-621,-685,-749,496,-590,750,749,734,748,974,989,1003,958,988,973,1002,942,987,957,972,1001,926,986,941,971,956,1000,910,985,925,999,894,970,-1071,-1087,-1102,1390,-1135,1436,1509,1451,1374,-1151,1405,1358,1480,1420,-1167,1507,1494,1389,1342,1465,1435,1450,1326,1505,1310,1493,1373,1479,1404,1492,1464,1419,428,443,472,397,736,526,464,464,486,457,442,471,484,482,1357,1449,1434,1478,1388,1491,1341,1490,1325,1489,1463,1403,1309,1477,1372,1448,1418,1433,1476,1356,1462,1387,-1439,1475,1340,1447,1402,1474,1324,1461,1371,1473,269,448,1432,1417,1308,1460,-1711,1459,-1727,1441,1099,1099,1446,1386,1431,1401,-1743,1289,1083,1083,1160,1160,1458,1445,1067,1067,1370,1457,1307,1430,1129,1129,1098,1098,268,432,267,416,266,400,-1887,1144,1187,1082,1173,1113,1186,1066,1050,1158,1128,1143,1172,1097,1171,1081,420,391,1157,1112,1170,1142,1127,1065,1169,1049,1156,1096,1141,1111,1155,1080,1126,1154,1064,1153,1140,1095,1048,-2159,1125,1110,1137,-2175,823,823,1139,1138,807,807,384,264,368,263,868,838,853,791,867,822,852,837,866,806,865,790,-2319,851,821,836,352,262,850,805,849,-2399,533,533,835,820,336,261,578,548,563,577,532,532,832,772,562,562,547,547,305,275,560,515,290,290,288,258 }; 1294 static const drmp3_uint8 tab32[] = { 130,162,193,209,44,28,76,140,9,9,9,9,9,9,9,9,190,254,222,238,126,94,157,157,109,61,173,205}; 1295 static const drmp3_uint8 tab33[] = { 252,236,220,204,188,172,156,140,124,108,92,76,60,44,28,12 }; 1296 static const drmp3_int16 tabindex[2*16] = { 0,32,64,98,0,132,180,218,292,364,426,538,648,746,0,1126,1460,1460,1460,1460,1460,1460,1460,1460,1842,1842,1842,1842,1842,1842,1842,1842 }; 1297 static const drmp3_uint8 g_linbits[] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,6,8,10,13,4,5,6,7,8,9,11,13 }; 1298 1299 #define DRMP3_PEEK_BITS(n) (bs_cache >> (32 - n)) 1300 #define DRMP3_FLUSH_BITS(n) { bs_cache <<= (n); bs_sh += (n); } 1301 #define DRMP3_CHECK_BITS while (bs_sh >= 0) { bs_cache |= (drmp3_uint32)*bs_next_ptr++ << bs_sh; bs_sh -= 8; } 1302 #define DRMP3_BSPOS ((bs_next_ptr - bs->buf)*8 - 24 + bs_sh) 1303 1304 float one = 0.0f; 1305 int ireg = 0, big_val_cnt = gr_info->big_values; 1306 const drmp3_uint8 *sfb = gr_info->sfbtab; 1307 const drmp3_uint8 *bs_next_ptr = bs->buf + bs->pos/8; 1308 drmp3_uint32 bs_cache = (((bs_next_ptr[0]*256u + bs_next_ptr[1])*256u + bs_next_ptr[2])*256u + bs_next_ptr[3]) << (bs->pos & 7); 1309 int pairs_to_decode, np, bs_sh = (bs->pos & 7) - 8; 1310 bs_next_ptr += 4; 1311 1312 while (big_val_cnt > 0) 1313 { 1314 int tab_num = gr_info->table_select[ireg]; 1315 int sfb_cnt = gr_info->region_count[ireg++]; 1316 const drmp3_int16 *codebook = tabs + tabindex[tab_num]; 1317 int linbits = g_linbits[tab_num]; 1318 if (linbits) 1319 { 1320 do 1321 { 1322 np = *sfb++ / 2; 1323 pairs_to_decode = DRMP3_MIN(big_val_cnt, np); 1324 one = *scf++; 1325 do 1326 { 1327 int j, w = 5; 1328 int leaf = codebook[DRMP3_PEEK_BITS(w)]; 1329 while (leaf < 0) 1330 { 1331 DRMP3_FLUSH_BITS(w); 1332 w = leaf & 7; 1333 leaf = codebook[DRMP3_PEEK_BITS(w) - (leaf >> 3)]; 1334 } 1335 DRMP3_FLUSH_BITS(leaf >> 8); 1336 1337 for (j = 0; j < 2; j++, dst++, leaf >>= 4) 1338 { 1339 int lsb = leaf & 0x0F; 1340 if (lsb == 15) 1341 { 1342 lsb += DRMP3_PEEK_BITS(linbits); 1343 DRMP3_FLUSH_BITS(linbits); 1344 DRMP3_CHECK_BITS; 1345 *dst = one*drmp3_L3_pow_43(lsb)*((drmp3_int32)bs_cache < 0 ? -1: 1); 1346 } else 1347 { 1348 *dst = g_drmp3_pow43[16 + lsb - 16*(bs_cache >> 31)]*one; 1349 } 1350 DRMP3_FLUSH_BITS(lsb ? 1 : 0); 1351 } 1352 DRMP3_CHECK_BITS; 1353 } while (--pairs_to_decode); 1354 } while ((big_val_cnt -= np) > 0 && --sfb_cnt >= 0); 1355 } else 1356 { 1357 do 1358 { 1359 np = *sfb++ / 2; 1360 pairs_to_decode = DRMP3_MIN(big_val_cnt, np); 1361 one = *scf++; 1362 do 1363 { 1364 int j, w = 5; 1365 int leaf = codebook[DRMP3_PEEK_BITS(w)]; 1366 while (leaf < 0) 1367 { 1368 DRMP3_FLUSH_BITS(w); 1369 w = leaf & 7; 1370 leaf = codebook[DRMP3_PEEK_BITS(w) - (leaf >> 3)]; 1371 } 1372 DRMP3_FLUSH_BITS(leaf >> 8); 1373 1374 for (j = 0; j < 2; j++, dst++, leaf >>= 4) 1375 { 1376 int lsb = leaf & 0x0F; 1377 *dst = g_drmp3_pow43[16 + lsb - 16*(bs_cache >> 31)]*one; 1378 DRMP3_FLUSH_BITS(lsb ? 1 : 0); 1379 } 1380 DRMP3_CHECK_BITS; 1381 } while (--pairs_to_decode); 1382 } while ((big_val_cnt -= np) > 0 && --sfb_cnt >= 0); 1383 } 1384 } 1385 1386 for (np = 1 - big_val_cnt;; dst += 4) 1387 { 1388 const drmp3_uint8 *codebook_count1 = (gr_info->count1_table) ? tab33 : tab32; 1389 int leaf = codebook_count1[DRMP3_PEEK_BITS(4)]; 1390 if (!(leaf & 8)) 1391 { 1392 leaf = codebook_count1[(leaf >> 3) + (bs_cache << 4 >> (32 - (leaf & 3)))]; 1393 } 1394 DRMP3_FLUSH_BITS(leaf & 7); 1395 if (DRMP3_BSPOS > layer3gr_limit) 1396 { 1397 break; 1398 } 1399 #define DRMP3_RELOAD_SCALEFACTOR if (!--np) { np = *sfb++/2; if (!np) break; one = *scf++; } 1400 #define DRMP3_DEQ_COUNT1(s) if (leaf & (128 >> s)) { dst[s] = ((drmp3_int32)bs_cache < 0) ? -one : one; DRMP3_FLUSH_BITS(1) } 1401 DRMP3_RELOAD_SCALEFACTOR; 1402 DRMP3_DEQ_COUNT1(0); 1403 DRMP3_DEQ_COUNT1(1); 1404 DRMP3_RELOAD_SCALEFACTOR; 1405 DRMP3_DEQ_COUNT1(2); 1406 DRMP3_DEQ_COUNT1(3); 1407 DRMP3_CHECK_BITS; 1408 } 1409 1410 bs->pos = layer3gr_limit; 1411 } 1412 1413 static void drmp3_L3_midside_stereo(float *left, int n) 1414 { 1415 int i = 0; 1416 float *right = left + 576; 1417 #if DRMP3_HAVE_SIMD 1418 if (drmp3_have_simd()) 1419 { 1420 for (; i < n - 3; i += 4) 1421 { 1422 drmp3_f4 vl = DRMP3_VLD(left + i); 1423 drmp3_f4 vr = DRMP3_VLD(right + i); 1424 DRMP3_VSTORE(left + i, DRMP3_VADD(vl, vr)); 1425 DRMP3_VSTORE(right + i, DRMP3_VSUB(vl, vr)); 1426 } 1427 #ifdef __GNUC__ 1428 /* Workaround for spurious -Waggressive-loop-optimizations warning from gcc. 1429 * For more info see: https://github.com/lieff/minimp3/issues/88 1430 */ 1431 if (__builtin_constant_p(n % 4 == 0) && n % 4 == 0) 1432 return; 1433 #endif 1434 } 1435 #endif 1436 for (; i < n; i++) 1437 { 1438 float a = left[i]; 1439 float b = right[i]; 1440 left[i] = a + b; 1441 right[i] = a - b; 1442 } 1443 } 1444 1445 static void drmp3_L3_intensity_stereo_band(float *left, int n, float kl, float kr) 1446 { 1447 int i; 1448 for (i = 0; i < n; i++) 1449 { 1450 left[i + 576] = left[i]*kr; 1451 left[i] = left[i]*kl; 1452 } 1453 } 1454 1455 static void drmp3_L3_stereo_top_band(const float *right, const drmp3_uint8 *sfb, int nbands, int max_band[3]) 1456 { 1457 int i, k; 1458 1459 max_band[0] = max_band[1] = max_band[2] = -1; 1460 1461 for (i = 0; i < nbands; i++) 1462 { 1463 for (k = 0; k < sfb[i]; k += 2) 1464 { 1465 if (right[k] != 0 || right[k + 1] != 0) 1466 { 1467 max_band[i % 3] = i; 1468 break; 1469 } 1470 } 1471 right += sfb[i]; 1472 } 1473 } 1474 1475 static void drmp3_L3_stereo_process(float *left, const drmp3_uint8 *ist_pos, const drmp3_uint8 *sfb, const drmp3_uint8 *hdr, int max_band[3], int mpeg2_sh) 1476 { 1477 static const float g_pan[7*2] = { 0,1,0.21132487f,0.78867513f,0.36602540f,0.63397460f,0.5f,0.5f,0.63397460f,0.36602540f,0.78867513f,0.21132487f,1,0 }; 1478 unsigned i, max_pos = DRMP3_HDR_TEST_MPEG1(hdr) ? 7 : 64; 1479 1480 for (i = 0; sfb[i]; i++) 1481 { 1482 unsigned ipos = ist_pos[i]; 1483 if ((int)i > max_band[i % 3] && ipos < max_pos) 1484 { 1485 float kl, kr, s = DRMP3_HDR_TEST_MS_STEREO(hdr) ? 1.41421356f : 1; 1486 if (DRMP3_HDR_TEST_MPEG1(hdr)) 1487 { 1488 kl = g_pan[2*ipos]; 1489 kr = g_pan[2*ipos + 1]; 1490 } else 1491 { 1492 kl = 1; 1493 kr = drmp3_L3_ldexp_q2(1, (ipos + 1) >> 1 << mpeg2_sh); 1494 if (ipos & 1) 1495 { 1496 kl = kr; 1497 kr = 1; 1498 } 1499 } 1500 drmp3_L3_intensity_stereo_band(left, sfb[i], kl*s, kr*s); 1501 } else if (DRMP3_HDR_TEST_MS_STEREO(hdr)) 1502 { 1503 drmp3_L3_midside_stereo(left, sfb[i]); 1504 } 1505 left += sfb[i]; 1506 } 1507 } 1508 1509 static void drmp3_L3_intensity_stereo(float *left, drmp3_uint8 *ist_pos, const drmp3_L3_gr_info *gr, const drmp3_uint8 *hdr) 1510 { 1511 int max_band[3], n_sfb = gr->n_long_sfb + gr->n_short_sfb; 1512 int i, max_blocks = gr->n_short_sfb ? 3 : 1; 1513 1514 drmp3_L3_stereo_top_band(left + 576, gr->sfbtab, n_sfb, max_band); 1515 if (gr->n_long_sfb) 1516 { 1517 max_band[0] = max_band[1] = max_band[2] = DRMP3_MAX(DRMP3_MAX(max_band[0], max_band[1]), max_band[2]); 1518 } 1519 for (i = 0; i < max_blocks; i++) 1520 { 1521 int default_pos = DRMP3_HDR_TEST_MPEG1(hdr) ? 3 : 0; 1522 int itop = n_sfb - max_blocks + i; 1523 int prev = itop - max_blocks; 1524 ist_pos[itop] = (drmp3_uint8)(max_band[i] >= prev ? default_pos : ist_pos[prev]); 1525 } 1526 drmp3_L3_stereo_process(left, ist_pos, gr->sfbtab, hdr, max_band, gr[1].scalefac_compress & 1); 1527 } 1528 1529 static void drmp3_L3_reorder(float *grbuf, float *scratch, const drmp3_uint8 *sfb) 1530 { 1531 int i, len; 1532 float *src = grbuf, *dst = scratch; 1533 1534 for (;0 != (len = *sfb); sfb += 3, src += 2*len) 1535 { 1536 for (i = 0; i < len; i++, src++) 1537 { 1538 *dst++ = src[0*len]; 1539 *dst++ = src[1*len]; 1540 *dst++ = src[2*len]; 1541 } 1542 } 1543 DRMP3_COPY_MEMORY(grbuf, scratch, (dst - scratch)*sizeof(float)); 1544 } 1545 1546 static void drmp3_L3_antialias(float *grbuf, int nbands) 1547 { 1548 static const float g_aa[2][8] = { 1549 {0.85749293f,0.88174200f,0.94962865f,0.98331459f,0.99551782f,0.99916056f,0.99989920f,0.99999316f}, 1550 {0.51449576f,0.47173197f,0.31337745f,0.18191320f,0.09457419f,0.04096558f,0.01419856f,0.00369997f} 1551 }; 1552 1553 for (; nbands > 0; nbands--, grbuf += 18) 1554 { 1555 int i = 0; 1556 #if DRMP3_HAVE_SIMD 1557 if (drmp3_have_simd()) for (; i < 8; i += 4) 1558 { 1559 drmp3_f4 vu = DRMP3_VLD(grbuf + 18 + i); 1560 drmp3_f4 vd = DRMP3_VLD(grbuf + 14 - i); 1561 drmp3_f4 vc0 = DRMP3_VLD(g_aa[0] + i); 1562 drmp3_f4 vc1 = DRMP3_VLD(g_aa[1] + i); 1563 vd = DRMP3_VREV(vd); 1564 DRMP3_VSTORE(grbuf + 18 + i, DRMP3_VSUB(DRMP3_VMUL(vu, vc0), DRMP3_VMUL(vd, vc1))); 1565 vd = DRMP3_VADD(DRMP3_VMUL(vu, vc1), DRMP3_VMUL(vd, vc0)); 1566 DRMP3_VSTORE(grbuf + 14 - i, DRMP3_VREV(vd)); 1567 } 1568 #endif 1569 #ifndef DR_MP3_ONLY_SIMD 1570 for(; i < 8; i++) 1571 { 1572 float u = grbuf[18 + i]; 1573 float d = grbuf[17 - i]; 1574 grbuf[18 + i] = u*g_aa[0][i] - d*g_aa[1][i]; 1575 grbuf[17 - i] = u*g_aa[1][i] + d*g_aa[0][i]; 1576 } 1577 #endif 1578 } 1579 } 1580 1581 static void drmp3_L3_dct3_9(float *y) 1582 { 1583 float s0, s1, s2, s3, s4, s5, s6, s7, s8, t0, t2, t4; 1584 1585 s0 = y[0]; s2 = y[2]; s4 = y[4]; s6 = y[6]; s8 = y[8]; 1586 t0 = s0 + s6*0.5f; 1587 s0 -= s6; 1588 t4 = (s4 + s2)*0.93969262f; 1589 t2 = (s8 + s2)*0.76604444f; 1590 s6 = (s4 - s8)*0.17364818f; 1591 s4 += s8 - s2; 1592 1593 s2 = s0 - s4*0.5f; 1594 y[4] = s4 + s0; 1595 s8 = t0 - t2 + s6; 1596 s0 = t0 - t4 + t2; 1597 s4 = t0 + t4 - s6; 1598 1599 s1 = y[1]; s3 = y[3]; s5 = y[5]; s7 = y[7]; 1600 1601 s3 *= 0.86602540f; 1602 t0 = (s5 + s1)*0.98480775f; 1603 t4 = (s5 - s7)*0.34202014f; 1604 t2 = (s1 + s7)*0.64278761f; 1605 s1 = (s1 - s5 - s7)*0.86602540f; 1606 1607 s5 = t0 - s3 - t2; 1608 s7 = t4 - s3 - t0; 1609 s3 = t4 + s3 - t2; 1610 1611 y[0] = s4 - s7; 1612 y[1] = s2 + s1; 1613 y[2] = s0 - s3; 1614 y[3] = s8 + s5; 1615 y[5] = s8 - s5; 1616 y[6] = s0 + s3; 1617 y[7] = s2 - s1; 1618 y[8] = s4 + s7; 1619 } 1620 1621 static void drmp3_L3_imdct36(float *grbuf, float *overlap, const float *window, int nbands) 1622 { 1623 int i, j; 1624 static const float g_twid9[18] = { 1625 0.73727734f,0.79335334f,0.84339145f,0.88701083f,0.92387953f,0.95371695f,0.97629601f,0.99144486f,0.99904822f,0.67559021f,0.60876143f,0.53729961f,0.46174861f,0.38268343f,0.30070580f,0.21643961f,0.13052619f,0.04361938f 1626 }; 1627 1628 for (j = 0; j < nbands; j++, grbuf += 18, overlap += 9) 1629 { 1630 float co[9], si[9]; 1631 co[0] = -grbuf[0]; 1632 si[0] = grbuf[17]; 1633 for (i = 0; i < 4; i++) 1634 { 1635 si[8 - 2*i] = grbuf[4*i + 1] - grbuf[4*i + 2]; 1636 co[1 + 2*i] = grbuf[4*i + 1] + grbuf[4*i + 2]; 1637 si[7 - 2*i] = grbuf[4*i + 4] - grbuf[4*i + 3]; 1638 co[2 + 2*i] = -(grbuf[4*i + 3] + grbuf[4*i + 4]); 1639 } 1640 drmp3_L3_dct3_9(co); 1641 drmp3_L3_dct3_9(si); 1642 1643 si[1] = -si[1]; 1644 si[3] = -si[3]; 1645 si[5] = -si[5]; 1646 si[7] = -si[7]; 1647 1648 i = 0; 1649 1650 #if DRMP3_HAVE_SIMD 1651 if (drmp3_have_simd()) for (; i < 8; i += 4) 1652 { 1653 drmp3_f4 vovl = DRMP3_VLD(overlap + i); 1654 drmp3_f4 vc = DRMP3_VLD(co + i); 1655 drmp3_f4 vs = DRMP3_VLD(si + i); 1656 drmp3_f4 vr0 = DRMP3_VLD(g_twid9 + i); 1657 drmp3_f4 vr1 = DRMP3_VLD(g_twid9 + 9 + i); 1658 drmp3_f4 vw0 = DRMP3_VLD(window + i); 1659 drmp3_f4 vw1 = DRMP3_VLD(window + 9 + i); 1660 drmp3_f4 vsum = DRMP3_VADD(DRMP3_VMUL(vc, vr1), DRMP3_VMUL(vs, vr0)); 1661 DRMP3_VSTORE(overlap + i, DRMP3_VSUB(DRMP3_VMUL(vc, vr0), DRMP3_VMUL(vs, vr1))); 1662 DRMP3_VSTORE(grbuf + i, DRMP3_VSUB(DRMP3_VMUL(vovl, vw0), DRMP3_VMUL(vsum, vw1))); 1663 vsum = DRMP3_VADD(DRMP3_VMUL(vovl, vw1), DRMP3_VMUL(vsum, vw0)); 1664 DRMP3_VSTORE(grbuf + 14 - i, DRMP3_VREV(vsum)); 1665 } 1666 #endif 1667 for (; i < 9; i++) 1668 { 1669 float ovl = overlap[i]; 1670 float sum = co[i]*g_twid9[9 + i] + si[i]*g_twid9[0 + i]; 1671 overlap[i] = co[i]*g_twid9[0 + i] - si[i]*g_twid9[9 + i]; 1672 grbuf[i] = ovl*window[0 + i] - sum*window[9 + i]; 1673 grbuf[17 - i] = ovl*window[9 + i] + sum*window[0 + i]; 1674 } 1675 } 1676 } 1677 1678 static void drmp3_L3_idct3(float x0, float x1, float x2, float *dst) 1679 { 1680 float m1 = x1*0.86602540f; 1681 float a1 = x0 - x2*0.5f; 1682 dst[1] = x0 + x2; 1683 dst[0] = a1 + m1; 1684 dst[2] = a1 - m1; 1685 } 1686 1687 static void drmp3_L3_imdct12(float *x, float *dst, float *overlap) 1688 { 1689 static const float g_twid3[6] = { 0.79335334f,0.92387953f,0.99144486f, 0.60876143f,0.38268343f,0.13052619f }; 1690 float co[3], si[3]; 1691 int i; 1692 1693 drmp3_L3_idct3(-x[0], x[6] + x[3], x[12] + x[9], co); 1694 drmp3_L3_idct3(x[15], x[12] - x[9], x[6] - x[3], si); 1695 si[1] = -si[1]; 1696 1697 for (i = 0; i < 3; i++) 1698 { 1699 float ovl = overlap[i]; 1700 float sum = co[i]*g_twid3[3 + i] + si[i]*g_twid3[0 + i]; 1701 overlap[i] = co[i]*g_twid3[0 + i] - si[i]*g_twid3[3 + i]; 1702 dst[i] = ovl*g_twid3[2 - i] - sum*g_twid3[5 - i]; 1703 dst[5 - i] = ovl*g_twid3[5 - i] + sum*g_twid3[2 - i]; 1704 } 1705 } 1706 1707 static void drmp3_L3_imdct_short(float *grbuf, float *overlap, int nbands) 1708 { 1709 for (;nbands > 0; nbands--, overlap += 9, grbuf += 18) 1710 { 1711 float tmp[18]; 1712 DRMP3_COPY_MEMORY(tmp, grbuf, sizeof(tmp)); 1713 DRMP3_COPY_MEMORY(grbuf, overlap, 6*sizeof(float)); 1714 drmp3_L3_imdct12(tmp, grbuf + 6, overlap + 6); 1715 drmp3_L3_imdct12(tmp + 1, grbuf + 12, overlap + 6); 1716 drmp3_L3_imdct12(tmp + 2, overlap, overlap + 6); 1717 } 1718 } 1719 1720 static void drmp3_L3_change_sign(float *grbuf) 1721 { 1722 int b, i; 1723 for (b = 0, grbuf += 18; b < 32; b += 2, grbuf += 36) 1724 for (i = 1; i < 18; i += 2) 1725 grbuf[i] = -grbuf[i]; 1726 } 1727 1728 static void drmp3_L3_imdct_gr(float *grbuf, float *overlap, unsigned block_type, unsigned n_long_bands) 1729 { 1730 static const float g_mdct_window[2][18] = { 1731 { 0.99904822f,0.99144486f,0.97629601f,0.95371695f,0.92387953f,0.88701083f,0.84339145f,0.79335334f,0.73727734f,0.04361938f,0.13052619f,0.21643961f,0.30070580f,0.38268343f,0.46174861f,0.53729961f,0.60876143f,0.67559021f }, 1732 { 1,1,1,1,1,1,0.99144486f,0.92387953f,0.79335334f,0,0,0,0,0,0,0.13052619f,0.38268343f,0.60876143f } 1733 }; 1734 if (n_long_bands) 1735 { 1736 drmp3_L3_imdct36(grbuf, overlap, g_mdct_window[0], n_long_bands); 1737 grbuf += 18*n_long_bands; 1738 overlap += 9*n_long_bands; 1739 } 1740 if (block_type == DRMP3_SHORT_BLOCK_TYPE) 1741 drmp3_L3_imdct_short(grbuf, overlap, 32 - n_long_bands); 1742 else 1743 drmp3_L3_imdct36(grbuf, overlap, g_mdct_window[block_type == DRMP3_STOP_BLOCK_TYPE], 32 - n_long_bands); 1744 } 1745 1746 static void drmp3_L3_save_reservoir(drmp3dec *h, drmp3dec_scratch *s) 1747 { 1748 int pos = (s->bs.pos + 7)/8u; 1749 int remains = s->bs.limit/8u - pos; 1750 if (remains > DRMP3_MAX_BITRESERVOIR_BYTES) 1751 { 1752 pos += remains - DRMP3_MAX_BITRESERVOIR_BYTES; 1753 remains = DRMP3_MAX_BITRESERVOIR_BYTES; 1754 } 1755 if (remains > 0) 1756 { 1757 DRMP3_MOVE_MEMORY(h->reserv_buf, s->maindata + pos, remains); 1758 } 1759 h->reserv = remains; 1760 } 1761 1762 static int drmp3_L3_restore_reservoir(drmp3dec *h, drmp3_bs *bs, drmp3dec_scratch *s, int main_data_begin) 1763 { 1764 int frame_bytes = (bs->limit - bs->pos)/8; 1765 int bytes_have = DRMP3_MIN(h->reserv, main_data_begin); 1766 DRMP3_COPY_MEMORY(s->maindata, h->reserv_buf + DRMP3_MAX(0, h->reserv - main_data_begin), DRMP3_MIN(h->reserv, main_data_begin)); 1767 DRMP3_COPY_MEMORY(s->maindata + bytes_have, bs->buf + bs->pos/8, frame_bytes); 1768 drmp3_bs_init(&s->bs, s->maindata, bytes_have + frame_bytes); 1769 return h->reserv >= main_data_begin; 1770 } 1771 1772 static void drmp3_L3_decode(drmp3dec *h, drmp3dec_scratch *s, drmp3_L3_gr_info *gr_info, int nch) 1773 { 1774 int ch; 1775 1776 for (ch = 0; ch < nch; ch++) 1777 { 1778 int layer3gr_limit = s->bs.pos + gr_info[ch].part_23_length; 1779 drmp3_L3_decode_scalefactors(h->header, s->ist_pos[ch], &s->bs, gr_info + ch, s->scf, ch); 1780 drmp3_L3_huffman(s->grbuf[ch], &s->bs, gr_info + ch, s->scf, layer3gr_limit); 1781 } 1782 1783 if (DRMP3_HDR_TEST_I_STEREO(h->header)) 1784 { 1785 drmp3_L3_intensity_stereo(s->grbuf[0], s->ist_pos[1], gr_info, h->header); 1786 } else if (DRMP3_HDR_IS_MS_STEREO(h->header)) 1787 { 1788 drmp3_L3_midside_stereo(s->grbuf[0], 576); 1789 } 1790 1791 for (ch = 0; ch < nch; ch++, gr_info++) 1792 { 1793 int aa_bands = 31; 1794 int n_long_bands = (gr_info->mixed_block_flag ? 2 : 0) << (int)(DRMP3_HDR_GET_MY_SAMPLE_RATE(h->header) == 2); 1795 1796 if (gr_info->n_short_sfb) 1797 { 1798 aa_bands = n_long_bands - 1; 1799 drmp3_L3_reorder(s->grbuf[ch] + n_long_bands*18, s->syn[0], gr_info->sfbtab + gr_info->n_long_sfb); 1800 } 1801 1802 drmp3_L3_antialias(s->grbuf[ch], aa_bands); 1803 drmp3_L3_imdct_gr(s->grbuf[ch], h->mdct_overlap[ch], gr_info->block_type, n_long_bands); 1804 drmp3_L3_change_sign(s->grbuf[ch]); 1805 } 1806 } 1807 1808 static void drmp3d_DCT_II(float *grbuf, int n) 1809 { 1810 static const float g_sec[24] = { 1811 10.19000816f,0.50060302f,0.50241929f,3.40760851f,0.50547093f,0.52249861f,2.05778098f,0.51544732f,0.56694406f,1.48416460f,0.53104258f,0.64682180f,1.16943991f,0.55310392f,0.78815460f,0.97256821f,0.58293498f,1.06067765f,0.83934963f,0.62250412f,1.72244716f,0.74453628f,0.67480832f,5.10114861f 1812 }; 1813 int i, k = 0; 1814 #if DRMP3_HAVE_SIMD 1815 if (drmp3_have_simd()) for (; k < n; k += 4) 1816 { 1817 drmp3_f4 t[4][8], *x; 1818 float *y = grbuf + k; 1819 1820 for (x = t[0], i = 0; i < 8; i++, x++) 1821 { 1822 drmp3_f4 x0 = DRMP3_VLD(&y[i*18]); 1823 drmp3_f4 x1 = DRMP3_VLD(&y[(15 - i)*18]); 1824 drmp3_f4 x2 = DRMP3_VLD(&y[(16 + i)*18]); 1825 drmp3_f4 x3 = DRMP3_VLD(&y[(31 - i)*18]); 1826 drmp3_f4 t0 = DRMP3_VADD(x0, x3); 1827 drmp3_f4 t1 = DRMP3_VADD(x1, x2); 1828 drmp3_f4 t2 = DRMP3_VMUL_S(DRMP3_VSUB(x1, x2), g_sec[3*i + 0]); 1829 drmp3_f4 t3 = DRMP3_VMUL_S(DRMP3_VSUB(x0, x3), g_sec[3*i + 1]); 1830 x[0] = DRMP3_VADD(t0, t1); 1831 x[8] = DRMP3_VMUL_S(DRMP3_VSUB(t0, t1), g_sec[3*i + 2]); 1832 x[16] = DRMP3_VADD(t3, t2); 1833 x[24] = DRMP3_VMUL_S(DRMP3_VSUB(t3, t2), g_sec[3*i + 2]); 1834 } 1835 for (x = t[0], i = 0; i < 4; i++, x += 8) 1836 { 1837 drmp3_f4 x0 = x[0], x1 = x[1], x2 = x[2], x3 = x[3], x4 = x[4], x5 = x[5], x6 = x[6], x7 = x[7], xt; 1838 xt = DRMP3_VSUB(x0, x7); x0 = DRMP3_VADD(x0, x7); 1839 x7 = DRMP3_VSUB(x1, x6); x1 = DRMP3_VADD(x1, x6); 1840 x6 = DRMP3_VSUB(x2, x5); x2 = DRMP3_VADD(x2, x5); 1841 x5 = DRMP3_VSUB(x3, x4); x3 = DRMP3_VADD(x3, x4); 1842 x4 = DRMP3_VSUB(x0, x3); x0 = DRMP3_VADD(x0, x3); 1843 x3 = DRMP3_VSUB(x1, x2); x1 = DRMP3_VADD(x1, x2); 1844 x[0] = DRMP3_VADD(x0, x1); 1845 x[4] = DRMP3_VMUL_S(DRMP3_VSUB(x0, x1), 0.70710677f); 1846 x5 = DRMP3_VADD(x5, x6); 1847 x6 = DRMP3_VMUL_S(DRMP3_VADD(x6, x7), 0.70710677f); 1848 x7 = DRMP3_VADD(x7, xt); 1849 x3 = DRMP3_VMUL_S(DRMP3_VADD(x3, x4), 0.70710677f); 1850 x5 = DRMP3_VSUB(x5, DRMP3_VMUL_S(x7, 0.198912367f)); /* rotate by PI/8 */ 1851 x7 = DRMP3_VADD(x7, DRMP3_VMUL_S(x5, 0.382683432f)); 1852 x5 = DRMP3_VSUB(x5, DRMP3_VMUL_S(x7, 0.198912367f)); 1853 x0 = DRMP3_VSUB(xt, x6); xt = DRMP3_VADD(xt, x6); 1854 x[1] = DRMP3_VMUL_S(DRMP3_VADD(xt, x7), 0.50979561f); 1855 x[2] = DRMP3_VMUL_S(DRMP3_VADD(x4, x3), 0.54119611f); 1856 x[3] = DRMP3_VMUL_S(DRMP3_VSUB(x0, x5), 0.60134488f); 1857 x[5] = DRMP3_VMUL_S(DRMP3_VADD(x0, x5), 0.89997619f); 1858 x[6] = DRMP3_VMUL_S(DRMP3_VSUB(x4, x3), 1.30656302f); 1859 x[7] = DRMP3_VMUL_S(DRMP3_VSUB(xt, x7), 2.56291556f); 1860 } 1861 1862 if (k > n - 3) 1863 { 1864 #if DRMP3_HAVE_SSE 1865 #define DRMP3_VSAVE2(i, v) _mm_storel_pi((__m64 *)(void*)&y[i*18], v) 1866 #else 1867 #define DRMP3_VSAVE2(i, v) vst1_f32((float32_t *)&y[i*18], vget_low_f32(v)) 1868 #endif 1869 for (i = 0; i < 7; i++, y += 4*18) 1870 { 1871 drmp3_f4 s = DRMP3_VADD(t[3][i], t[3][i + 1]); 1872 DRMP3_VSAVE2(0, t[0][i]); 1873 DRMP3_VSAVE2(1, DRMP3_VADD(t[2][i], s)); 1874 DRMP3_VSAVE2(2, DRMP3_VADD(t[1][i], t[1][i + 1])); 1875 DRMP3_VSAVE2(3, DRMP3_VADD(t[2][1 + i], s)); 1876 } 1877 DRMP3_VSAVE2(0, t[0][7]); 1878 DRMP3_VSAVE2(1, DRMP3_VADD(t[2][7], t[3][7])); 1879 DRMP3_VSAVE2(2, t[1][7]); 1880 DRMP3_VSAVE2(3, t[3][7]); 1881 } else 1882 { 1883 #define DRMP3_VSAVE4(i, v) DRMP3_VSTORE(&y[i*18], v) 1884 for (i = 0; i < 7; i++, y += 4*18) 1885 { 1886 drmp3_f4 s = DRMP3_VADD(t[3][i], t[3][i + 1]); 1887 DRMP3_VSAVE4(0, t[0][i]); 1888 DRMP3_VSAVE4(1, DRMP3_VADD(t[2][i], s)); 1889 DRMP3_VSAVE4(2, DRMP3_VADD(t[1][i], t[1][i + 1])); 1890 DRMP3_VSAVE4(3, DRMP3_VADD(t[2][1 + i], s)); 1891 } 1892 DRMP3_VSAVE4(0, t[0][7]); 1893 DRMP3_VSAVE4(1, DRMP3_VADD(t[2][7], t[3][7])); 1894 DRMP3_VSAVE4(2, t[1][7]); 1895 DRMP3_VSAVE4(3, t[3][7]); 1896 } 1897 } else 1898 #endif 1899 #ifdef DR_MP3_ONLY_SIMD 1900 {} /* for HAVE_SIMD=1, MINIMP3_ONLY_SIMD=1 case we do not need non-intrinsic "else" branch */ 1901 #else 1902 for (; k < n; k++) 1903 { 1904 float t[4][8], *x, *y = grbuf + k; 1905 1906 for (x = t[0], i = 0; i < 8; i++, x++) 1907 { 1908 float x0 = y[i*18]; 1909 float x1 = y[(15 - i)*18]; 1910 float x2 = y[(16 + i)*18]; 1911 float x3 = y[(31 - i)*18]; 1912 float t0 = x0 + x3; 1913 float t1 = x1 + x2; 1914 float t2 = (x1 - x2)*g_sec[3*i + 0]; 1915 float t3 = (x0 - x3)*g_sec[3*i + 1]; 1916 x[0] = t0 + t1; 1917 x[8] = (t0 - t1)*g_sec[3*i + 2]; 1918 x[16] = t3 + t2; 1919 x[24] = (t3 - t2)*g_sec[3*i + 2]; 1920 } 1921 for (x = t[0], i = 0; i < 4; i++, x += 8) 1922 { 1923 float x0 = x[0], x1 = x[1], x2 = x[2], x3 = x[3], x4 = x[4], x5 = x[5], x6 = x[6], x7 = x[7], xt; 1924 xt = x0 - x7; x0 += x7; 1925 x7 = x1 - x6; x1 += x6; 1926 x6 = x2 - x5; x2 += x5; 1927 x5 = x3 - x4; x3 += x4; 1928 x4 = x0 - x3; x0 += x3; 1929 x3 = x1 - x2; x1 += x2; 1930 x[0] = x0 + x1; 1931 x[4] = (x0 - x1)*0.70710677f; 1932 x5 = x5 + x6; 1933 x6 = (x6 + x7)*0.70710677f; 1934 x7 = x7 + xt; 1935 x3 = (x3 + x4)*0.70710677f; 1936 x5 -= x7*0.198912367f; /* rotate by PI/8 */ 1937 x7 += x5*0.382683432f; 1938 x5 -= x7*0.198912367f; 1939 x0 = xt - x6; xt += x6; 1940 x[1] = (xt + x7)*0.50979561f; 1941 x[2] = (x4 + x3)*0.54119611f; 1942 x[3] = (x0 - x5)*0.60134488f; 1943 x[5] = (x0 + x5)*0.89997619f; 1944 x[6] = (x4 - x3)*1.30656302f; 1945 x[7] = (xt - x7)*2.56291556f; 1946 1947 } 1948 for (i = 0; i < 7; i++, y += 4*18) 1949 { 1950 y[0*18] = t[0][i]; 1951 y[1*18] = t[2][i] + t[3][i] + t[3][i + 1]; 1952 y[2*18] = t[1][i] + t[1][i + 1]; 1953 y[3*18] = t[2][i + 1] + t[3][i] + t[3][i + 1]; 1954 } 1955 y[0*18] = t[0][7]; 1956 y[1*18] = t[2][7] + t[3][7]; 1957 y[2*18] = t[1][7]; 1958 y[3*18] = t[3][7]; 1959 } 1960 #endif 1961 } 1962 1963 #ifndef DR_MP3_FLOAT_OUTPUT 1964 typedef drmp3_int16 drmp3d_sample_t; 1965 1966 static drmp3_int16 drmp3d_scale_pcm(float sample) 1967 { 1968 drmp3_int16 s; 1969 #if DRMP3_HAVE_ARMV6 1970 drmp3_int32 s32 = (drmp3_int32)(sample + .5f); 1971 s32 -= (s32 < 0); 1972 s = (drmp3_int16)drmp3_clip_int16_arm(s32); 1973 #else 1974 if (sample >= 32766.5) return (drmp3_int16) 32767; 1975 if (sample <= -32767.5) return (drmp3_int16)-32768; 1976 s = (drmp3_int16)(sample + .5f); 1977 s -= (s < 0); /* away from zero, to be compliant */ 1978 #endif 1979 return s; 1980 } 1981 #else 1982 typedef float drmp3d_sample_t; 1983 1984 static float drmp3d_scale_pcm(float sample) 1985 { 1986 return sample*(1.f/32768.f); 1987 } 1988 #endif 1989 1990 static void drmp3d_synth_pair(drmp3d_sample_t *pcm, int nch, const float *z) 1991 { 1992 float a; 1993 a = (z[14*64] - z[ 0]) * 29; 1994 a += (z[ 1*64] + z[13*64]) * 213; 1995 a += (z[12*64] - z[ 2*64]) * 459; 1996 a += (z[ 3*64] + z[11*64]) * 2037; 1997 a += (z[10*64] - z[ 4*64]) * 5153; 1998 a += (z[ 5*64] + z[ 9*64]) * 6574; 1999 a += (z[ 8*64] - z[ 6*64]) * 37489; 2000 a += z[ 7*64] * 75038; 2001 pcm[0] = drmp3d_scale_pcm(a); 2002 2003 z += 2; 2004 a = z[14*64] * 104; 2005 a += z[12*64] * 1567; 2006 a += z[10*64] * 9727; 2007 a += z[ 8*64] * 64019; 2008 a += z[ 6*64] * -9975; 2009 a += z[ 4*64] * -45; 2010 a += z[ 2*64] * 146; 2011 a += z[ 0*64] * -5; 2012 pcm[16*nch] = drmp3d_scale_pcm(a); 2013 } 2014 2015 static void drmp3d_synth(float *xl, drmp3d_sample_t *dstl, int nch, float *lins) 2016 { 2017 int i; 2018 float *xr = xl + 576*(nch - 1); 2019 drmp3d_sample_t *dstr = dstl + (nch - 1); 2020 2021 static const float g_win[] = { 2022 -1,26,-31,208,218,401,-519,2063,2000,4788,-5517,7134,5959,35640,-39336,74992, 2023 -1,24,-35,202,222,347,-581,2080,1952,4425,-5879,7640,5288,33791,-41176,74856, 2024 -1,21,-38,196,225,294,-645,2087,1893,4063,-6237,8092,4561,31947,-43006,74630, 2025 -1,19,-41,190,227,244,-711,2085,1822,3705,-6589,8492,3776,30112,-44821,74313, 2026 -1,17,-45,183,228,197,-779,2075,1739,3351,-6935,8840,2935,28289,-46617,73908, 2027 -1,16,-49,176,228,153,-848,2057,1644,3004,-7271,9139,2037,26482,-48390,73415, 2028 -2,14,-53,169,227,111,-919,2032,1535,2663,-7597,9389,1082,24694,-50137,72835, 2029 -2,13,-58,161,224,72,-991,2001,1414,2330,-7910,9592,70,22929,-51853,72169, 2030 -2,11,-63,154,221,36,-1064,1962,1280,2006,-8209,9750,-998,21189,-53534,71420, 2031 -2,10,-68,147,215,2,-1137,1919,1131,1692,-8491,9863,-2122,19478,-55178,70590, 2032 -3,9,-73,139,208,-29,-1210,1870,970,1388,-8755,9935,-3300,17799,-56778,69679, 2033 -3,8,-79,132,200,-57,-1283,1817,794,1095,-8998,9966,-4533,16155,-58333,68692, 2034 -4,7,-85,125,189,-83,-1356,1759,605,814,-9219,9959,-5818,14548,-59838,67629, 2035 -4,7,-91,117,177,-106,-1428,1698,402,545,-9416,9916,-7154,12980,-61289,66494, 2036 -5,6,-97,111,163,-127,-1498,1634,185,288,-9585,9838,-8540,11455,-62684,65290 2037 }; 2038 float *zlin = lins + 15*64; 2039 const float *w = g_win; 2040 2041 zlin[4*15] = xl[18*16]; 2042 zlin[4*15 + 1] = xr[18*16]; 2043 zlin[4*15 + 2] = xl[0]; 2044 zlin[4*15 + 3] = xr[0]; 2045 2046 zlin[4*31] = xl[1 + 18*16]; 2047 zlin[4*31 + 1] = xr[1 + 18*16]; 2048 zlin[4*31 + 2] = xl[1]; 2049 zlin[4*31 + 3] = xr[1]; 2050 2051 drmp3d_synth_pair(dstr, nch, lins + 4*15 + 1); 2052 drmp3d_synth_pair(dstr + 32*nch, nch, lins + 4*15 + 64 + 1); 2053 drmp3d_synth_pair(dstl, nch, lins + 4*15); 2054 drmp3d_synth_pair(dstl + 32*nch, nch, lins + 4*15 + 64); 2055 2056 #if DRMP3_HAVE_SIMD 2057 if (drmp3_have_simd()) for (i = 14; i >= 0; i--) 2058 { 2059 #define DRMP3_VLOAD(k) drmp3_f4 w0 = DRMP3_VSET(*w++); drmp3_f4 w1 = DRMP3_VSET(*w++); drmp3_f4 vz = DRMP3_VLD(&zlin[4*i - 64*k]); drmp3_f4 vy = DRMP3_VLD(&zlin[4*i - 64*(15 - k)]); 2060 #define DRMP3_V0(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0)) ; a = DRMP3_VSUB(DRMP3_VMUL(vz, w0), DRMP3_VMUL(vy, w1)); } 2061 #define DRMP3_V1(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(b, DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0))); a = DRMP3_VADD(a, DRMP3_VSUB(DRMP3_VMUL(vz, w0), DRMP3_VMUL(vy, w1))); } 2062 #define DRMP3_V2(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(b, DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0))); a = DRMP3_VADD(a, DRMP3_VSUB(DRMP3_VMUL(vy, w1), DRMP3_VMUL(vz, w0))); } 2063 drmp3_f4 a, b; 2064 zlin[4*i] = xl[18*(31 - i)]; 2065 zlin[4*i + 1] = xr[18*(31 - i)]; 2066 zlin[4*i + 2] = xl[1 + 18*(31 - i)]; 2067 zlin[4*i + 3] = xr[1 + 18*(31 - i)]; 2068 zlin[4*i + 64] = xl[1 + 18*(1 + i)]; 2069 zlin[4*i + 64 + 1] = xr[1 + 18*(1 + i)]; 2070 zlin[4*i - 64 + 2] = xl[18*(1 + i)]; 2071 zlin[4*i - 64 + 3] = xr[18*(1 + i)]; 2072 2073 DRMP3_V0(0) DRMP3_V2(1) DRMP3_V1(2) DRMP3_V2(3) DRMP3_V1(4) DRMP3_V2(5) DRMP3_V1(6) DRMP3_V2(7) 2074 2075 { 2076 #ifndef DR_MP3_FLOAT_OUTPUT 2077 #if DRMP3_HAVE_SSE 2078 static const drmp3_f4 g_max = { 32767.0f, 32767.0f, 32767.0f, 32767.0f }; 2079 static const drmp3_f4 g_min = { -32768.0f, -32768.0f, -32768.0f, -32768.0f }; 2080 __m128i pcm8 = _mm_packs_epi32(_mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(a, g_max), g_min)), 2081 _mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(b, g_max), g_min))); 2082 dstr[(15 - i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 1); 2083 dstr[(17 + i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 5); 2084 dstl[(15 - i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 0); 2085 dstl[(17 + i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 4); 2086 dstr[(47 - i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 3); 2087 dstr[(49 + i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 7); 2088 dstl[(47 - i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 2); 2089 dstl[(49 + i)*nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 6); 2090 #else 2091 int16x4_t pcma, pcmb; 2092 a = DRMP3_VADD(a, DRMP3_VSET(0.5f)); 2093 b = DRMP3_VADD(b, DRMP3_VSET(0.5f)); 2094 pcma = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(a), vreinterpretq_s32_u32(vcltq_f32(a, DRMP3_VSET(0))))); 2095 pcmb = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(b), vreinterpretq_s32_u32(vcltq_f32(b, DRMP3_VSET(0))))); 2096 vst1_lane_s16(dstr + (15 - i)*nch, pcma, 1); 2097 vst1_lane_s16(dstr + (17 + i)*nch, pcmb, 1); 2098 vst1_lane_s16(dstl + (15 - i)*nch, pcma, 0); 2099 vst1_lane_s16(dstl + (17 + i)*nch, pcmb, 0); 2100 vst1_lane_s16(dstr + (47 - i)*nch, pcma, 3); 2101 vst1_lane_s16(dstr + (49 + i)*nch, pcmb, 3); 2102 vst1_lane_s16(dstl + (47 - i)*nch, pcma, 2); 2103 vst1_lane_s16(dstl + (49 + i)*nch, pcmb, 2); 2104 #endif 2105 #else 2106 static const drmp3_f4 g_scale = { 1.0f/32768.0f, 1.0f/32768.0f, 1.0f/32768.0f, 1.0f/32768.0f }; 2107 a = DRMP3_VMUL(a, g_scale); 2108 b = DRMP3_VMUL(b, g_scale); 2109 #if DRMP3_HAVE_SSE 2110 _mm_store_ss(dstr + (15 - i)*nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(1, 1, 1, 1))); 2111 _mm_store_ss(dstr + (17 + i)*nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(1, 1, 1, 1))); 2112 _mm_store_ss(dstl + (15 - i)*nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(0, 0, 0, 0))); 2113 _mm_store_ss(dstl + (17 + i)*nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(0, 0, 0, 0))); 2114 _mm_store_ss(dstr + (47 - i)*nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(3, 3, 3, 3))); 2115 _mm_store_ss(dstr + (49 + i)*nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(3, 3, 3, 3))); 2116 _mm_store_ss(dstl + (47 - i)*nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(2, 2, 2, 2))); 2117 _mm_store_ss(dstl + (49 + i)*nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(2, 2, 2, 2))); 2118 #else 2119 vst1q_lane_f32(dstr + (15 - i)*nch, a, 1); 2120 vst1q_lane_f32(dstr + (17 + i)*nch, b, 1); 2121 vst1q_lane_f32(dstl + (15 - i)*nch, a, 0); 2122 vst1q_lane_f32(dstl + (17 + i)*nch, b, 0); 2123 vst1q_lane_f32(dstr + (47 - i)*nch, a, 3); 2124 vst1q_lane_f32(dstr + (49 + i)*nch, b, 3); 2125 vst1q_lane_f32(dstl + (47 - i)*nch, a, 2); 2126 vst1q_lane_f32(dstl + (49 + i)*nch, b, 2); 2127 #endif 2128 #endif /* DR_MP3_FLOAT_OUTPUT */ 2129 } 2130 } else 2131 #endif 2132 #ifdef DR_MP3_ONLY_SIMD 2133 {} /* for HAVE_SIMD=1, MINIMP3_ONLY_SIMD=1 case we do not need non-intrinsic "else" branch */ 2134 #else 2135 for (i = 14; i >= 0; i--) 2136 { 2137 #define DRMP3_LOAD(k) float w0 = *w++; float w1 = *w++; float *vz = &zlin[4*i - k*64]; float *vy = &zlin[4*i - (15 - k)*64]; 2138 #define DRMP3_S0(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] = vz[j]*w1 + vy[j]*w0, a[j] = vz[j]*w0 - vy[j]*w1; } 2139 #define DRMP3_S1(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] += vz[j]*w1 + vy[j]*w0, a[j] += vz[j]*w0 - vy[j]*w1; } 2140 #define DRMP3_S2(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] += vz[j]*w1 + vy[j]*w0, a[j] += vy[j]*w1 - vz[j]*w0; } 2141 float a[4], b[4]; 2142 2143 zlin[4*i] = xl[18*(31 - i)]; 2144 zlin[4*i + 1] = xr[18*(31 - i)]; 2145 zlin[4*i + 2] = xl[1 + 18*(31 - i)]; 2146 zlin[4*i + 3] = xr[1 + 18*(31 - i)]; 2147 zlin[4*(i + 16)] = xl[1 + 18*(1 + i)]; 2148 zlin[4*(i + 16) + 1] = xr[1 + 18*(1 + i)]; 2149 zlin[4*(i - 16) + 2] = xl[18*(1 + i)]; 2150 zlin[4*(i - 16) + 3] = xr[18*(1 + i)]; 2151 2152 DRMP3_S0(0) DRMP3_S2(1) DRMP3_S1(2) DRMP3_S2(3) DRMP3_S1(4) DRMP3_S2(5) DRMP3_S1(6) DRMP3_S2(7) 2153 2154 dstr[(15 - i)*nch] = drmp3d_scale_pcm(a[1]); 2155 dstr[(17 + i)*nch] = drmp3d_scale_pcm(b[1]); 2156 dstl[(15 - i)*nch] = drmp3d_scale_pcm(a[0]); 2157 dstl[(17 + i)*nch] = drmp3d_scale_pcm(b[0]); 2158 dstr[(47 - i)*nch] = drmp3d_scale_pcm(a[3]); 2159 dstr[(49 + i)*nch] = drmp3d_scale_pcm(b[3]); 2160 dstl[(47 - i)*nch] = drmp3d_scale_pcm(a[2]); 2161 dstl[(49 + i)*nch] = drmp3d_scale_pcm(b[2]); 2162 } 2163 #endif 2164 } 2165 2166 static void drmp3d_synth_granule(float *qmf_state, float *grbuf, int nbands, int nch, drmp3d_sample_t *pcm, float *lins) 2167 { 2168 int i; 2169 for (i = 0; i < nch; i++) 2170 { 2171 drmp3d_DCT_II(grbuf + 576*i, nbands); 2172 } 2173 2174 DRMP3_COPY_MEMORY(lins, qmf_state, sizeof(float)*15*64); 2175 2176 for (i = 0; i < nbands; i += 2) 2177 { 2178 drmp3d_synth(grbuf + i, pcm + 32*nch*i, nch, lins + i*64); 2179 } 2180 #ifndef DR_MP3_NONSTANDARD_BUT_LOGICAL 2181 if (nch == 1) 2182 { 2183 for (i = 0; i < 15*64; i += 2) 2184 { 2185 qmf_state[i] = lins[nbands*64 + i]; 2186 } 2187 } else 2188 #endif 2189 { 2190 DRMP3_COPY_MEMORY(qmf_state, lins + nbands*64, sizeof(float)*15*64); 2191 } 2192 } 2193 2194 static int drmp3d_match_frame(const drmp3_uint8 *hdr, int mp3_bytes, int frame_bytes) 2195 { 2196 int i, nmatch; 2197 for (i = 0, nmatch = 0; nmatch < DRMP3_MAX_FRAME_SYNC_MATCHES; nmatch++) 2198 { 2199 i += drmp3_hdr_frame_bytes(hdr + i, frame_bytes) + drmp3_hdr_padding(hdr + i); 2200 if (i + DRMP3_HDR_SIZE > mp3_bytes) 2201 return nmatch > 0; 2202 if (!drmp3_hdr_compare(hdr, hdr + i)) 2203 return 0; 2204 } 2205 return 1; 2206 } 2207 2208 static int drmp3d_find_frame(const drmp3_uint8 *mp3, int mp3_bytes, int *free_format_bytes, int *ptr_frame_bytes) 2209 { 2210 int i, k; 2211 for (i = 0; i < mp3_bytes - DRMP3_HDR_SIZE; i++, mp3++) 2212 { 2213 if (drmp3_hdr_valid(mp3)) 2214 { 2215 int frame_bytes = drmp3_hdr_frame_bytes(mp3, *free_format_bytes); 2216 int frame_and_padding = frame_bytes + drmp3_hdr_padding(mp3); 2217 2218 for (k = DRMP3_HDR_SIZE; !frame_bytes && k < DRMP3_MAX_FREE_FORMAT_FRAME_SIZE && i + 2*k < mp3_bytes - DRMP3_HDR_SIZE; k++) 2219 { 2220 if (drmp3_hdr_compare(mp3, mp3 + k)) 2221 { 2222 int fb = k - drmp3_hdr_padding(mp3); 2223 int nextfb = fb + drmp3_hdr_padding(mp3 + k); 2224 if (i + k + nextfb + DRMP3_HDR_SIZE > mp3_bytes || !drmp3_hdr_compare(mp3, mp3 + k + nextfb)) 2225 continue; 2226 frame_and_padding = k; 2227 frame_bytes = fb; 2228 *free_format_bytes = fb; 2229 } 2230 } 2231 2232 if ((frame_bytes && i + frame_and_padding <= mp3_bytes && 2233 drmp3d_match_frame(mp3, mp3_bytes - i, frame_bytes)) || 2234 (!i && frame_and_padding == mp3_bytes)) 2235 { 2236 *ptr_frame_bytes = frame_and_padding; 2237 return i; 2238 } 2239 *free_format_bytes = 0; 2240 } 2241 } 2242 *ptr_frame_bytes = 0; 2243 return mp3_bytes; 2244 } 2245 2246 DRMP3_API void drmp3dec_init(drmp3dec *dec) 2247 { 2248 dec->header[0] = 0; 2249 } 2250 2251 DRMP3_API int drmp3dec_decode_frame(drmp3dec *dec, const drmp3_uint8 *mp3, int mp3_bytes, void *pcm, drmp3dec_frame_info *info) 2252 { 2253 int i = 0, igr, frame_size = 0, success = 1; 2254 const drmp3_uint8 *hdr; 2255 drmp3_bs bs_frame[1]; 2256 drmp3dec_scratch scratch; 2257 2258 if (mp3_bytes > 4 && dec->header[0] == 0xff && drmp3_hdr_compare(dec->header, mp3)) 2259 { 2260 frame_size = drmp3_hdr_frame_bytes(mp3, dec->free_format_bytes) + drmp3_hdr_padding(mp3); 2261 if (frame_size != mp3_bytes && (frame_size + DRMP3_HDR_SIZE > mp3_bytes || !drmp3_hdr_compare(mp3, mp3 + frame_size))) 2262 { 2263 frame_size = 0; 2264 } 2265 } 2266 if (!frame_size) 2267 { 2268 DRMP3_ZERO_MEMORY(dec, sizeof(drmp3dec)); 2269 i = drmp3d_find_frame(mp3, mp3_bytes, &dec->free_format_bytes, &frame_size); 2270 if (!frame_size || i + frame_size > mp3_bytes) 2271 { 2272 info->frame_bytes = i; 2273 return 0; 2274 } 2275 } 2276 2277 hdr = mp3 + i; 2278 DRMP3_COPY_MEMORY(dec->header, hdr, DRMP3_HDR_SIZE); 2279 info->frame_bytes = i + frame_size; 2280 info->channels = DRMP3_HDR_IS_MONO(hdr) ? 1 : 2; 2281 info->hz = drmp3_hdr_sample_rate_hz(hdr); 2282 info->layer = 4 - DRMP3_HDR_GET_LAYER(hdr); 2283 info->bitrate_kbps = drmp3_hdr_bitrate_kbps(hdr); 2284 2285 drmp3_bs_init(bs_frame, hdr + DRMP3_HDR_SIZE, frame_size - DRMP3_HDR_SIZE); 2286 if (DRMP3_HDR_IS_CRC(hdr)) 2287 { 2288 drmp3_bs_get_bits(bs_frame, 16); 2289 } 2290 2291 if (info->layer == 3) 2292 { 2293 int main_data_begin = drmp3_L3_read_side_info(bs_frame, scratch.gr_info, hdr); 2294 if (main_data_begin < 0 || bs_frame->pos > bs_frame->limit) 2295 { 2296 drmp3dec_init(dec); 2297 return 0; 2298 } 2299 success = drmp3_L3_restore_reservoir(dec, bs_frame, &scratch, main_data_begin); 2300 if (success && pcm != NULL) 2301 { 2302 for (igr = 0; igr < (DRMP3_HDR_TEST_MPEG1(hdr) ? 2 : 1); igr++, pcm = DRMP3_OFFSET_PTR(pcm, sizeof(drmp3d_sample_t)*576*info->channels)) 2303 { 2304 DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576*2*sizeof(float)); 2305 drmp3_L3_decode(dec, &scratch, scratch.gr_info + igr*info->channels, info->channels); 2306 drmp3d_synth_granule(dec->qmf_state, scratch.grbuf[0], 18, info->channels, (drmp3d_sample_t*)pcm, scratch.syn[0]); 2307 } 2308 } 2309 drmp3_L3_save_reservoir(dec, &scratch); 2310 } else 2311 { 2312 #ifdef DR_MP3_ONLY_MP3 2313 return 0; 2314 #else 2315 drmp3_L12_scale_info sci[1]; 2316 2317 if (pcm == NULL) { 2318 return drmp3_hdr_frame_samples(hdr); 2319 } 2320 2321 drmp3_L12_read_scale_info(hdr, bs_frame, sci); 2322 2323 DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576*2*sizeof(float)); 2324 for (i = 0, igr = 0; igr < 3; igr++) 2325 { 2326 if (12 == (i += drmp3_L12_dequantize_granule(scratch.grbuf[0] + i, bs_frame, sci, info->layer | 1))) 2327 { 2328 i = 0; 2329 drmp3_L12_apply_scf_384(sci, sci->scf + igr, scratch.grbuf[0]); 2330 drmp3d_synth_granule(dec->qmf_state, scratch.grbuf[0], 12, info->channels, (drmp3d_sample_t*)pcm, scratch.syn[0]); 2331 DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576*2*sizeof(float)); 2332 pcm = DRMP3_OFFSET_PTR(pcm, sizeof(drmp3d_sample_t)*384*info->channels); 2333 } 2334 if (bs_frame->pos > bs_frame->limit) 2335 { 2336 drmp3dec_init(dec); 2337 return 0; 2338 } 2339 } 2340 #endif 2341 } 2342 2343 return success*drmp3_hdr_frame_samples(dec->header); 2344 } 2345 2346 DRMP3_API void drmp3dec_f32_to_s16(const float *in, drmp3_int16 *out, size_t num_samples) 2347 { 2348 size_t i = 0; 2349 #if DRMP3_HAVE_SIMD 2350 size_t aligned_count = num_samples & ~7; 2351 for(; i < aligned_count; i+=8) 2352 { 2353 drmp3_f4 scale = DRMP3_VSET(32768.0f); 2354 drmp3_f4 a = DRMP3_VMUL(DRMP3_VLD(&in[i ]), scale); 2355 drmp3_f4 b = DRMP3_VMUL(DRMP3_VLD(&in[i+4]), scale); 2356 #if DRMP3_HAVE_SSE 2357 drmp3_f4 s16max = DRMP3_VSET( 32767.0f); 2358 drmp3_f4 s16min = DRMP3_VSET(-32768.0f); 2359 __m128i pcm8 = _mm_packs_epi32(_mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(a, s16max), s16min)), 2360 _mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(b, s16max), s16min))); 2361 out[i ] = (drmp3_int16)_mm_extract_epi16(pcm8, 0); 2362 out[i+1] = (drmp3_int16)_mm_extract_epi16(pcm8, 1); 2363 out[i+2] = (drmp3_int16)_mm_extract_epi16(pcm8, 2); 2364 out[i+3] = (drmp3_int16)_mm_extract_epi16(pcm8, 3); 2365 out[i+4] = (drmp3_int16)_mm_extract_epi16(pcm8, 4); 2366 out[i+5] = (drmp3_int16)_mm_extract_epi16(pcm8, 5); 2367 out[i+6] = (drmp3_int16)_mm_extract_epi16(pcm8, 6); 2368 out[i+7] = (drmp3_int16)_mm_extract_epi16(pcm8, 7); 2369 #else 2370 int16x4_t pcma, pcmb; 2371 a = DRMP3_VADD(a, DRMP3_VSET(0.5f)); 2372 b = DRMP3_VADD(b, DRMP3_VSET(0.5f)); 2373 pcma = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(a), vreinterpretq_s32_u32(vcltq_f32(a, DRMP3_VSET(0))))); 2374 pcmb = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(b), vreinterpretq_s32_u32(vcltq_f32(b, DRMP3_VSET(0))))); 2375 vst1_lane_s16(out+i , pcma, 0); 2376 vst1_lane_s16(out+i+1, pcma, 1); 2377 vst1_lane_s16(out+i+2, pcma, 2); 2378 vst1_lane_s16(out+i+3, pcma, 3); 2379 vst1_lane_s16(out+i+4, pcmb, 0); 2380 vst1_lane_s16(out+i+5, pcmb, 1); 2381 vst1_lane_s16(out+i+6, pcmb, 2); 2382 vst1_lane_s16(out+i+7, pcmb, 3); 2383 #endif 2384 } 2385 #endif 2386 for(; i < num_samples; i++) 2387 { 2388 float sample = in[i] * 32768.0f; 2389 if (sample >= 32766.5) 2390 out[i] = (drmp3_int16) 32767; 2391 else if (sample <= -32767.5) 2392 out[i] = (drmp3_int16)-32768; 2393 else 2394 { 2395 short s = (drmp3_int16)(sample + .5f); 2396 s -= (s < 0); /* away from zero, to be compliant */ 2397 out[i] = s; 2398 } 2399 } 2400 } 2401 2402 2403 2404 /************************************************************************************************************************************************************ 2405 2406 Main Public API 2407 2408 ************************************************************************************************************************************************************/ 2409 #include <math.h> /* For sin() and exp(). */ 2410 2411 #if defined(SIZE_MAX) 2412 #define DRMP3_SIZE_MAX SIZE_MAX 2413 #else 2414 #if defined(_WIN64) || defined(_LP64) || defined(__LP64__) 2415 #define DRMP3_SIZE_MAX ((drmp3_uint64)0xFFFFFFFFFFFFFFFF) 2416 #else 2417 #define DRMP3_SIZE_MAX 0xFFFFFFFF 2418 #endif 2419 #endif 2420 2421 /* Options. */ 2422 #ifndef DRMP3_SEEK_LEADING_MP3_FRAMES 2423 #define DRMP3_SEEK_LEADING_MP3_FRAMES 2 2424 #endif 2425 2426 #define DRMP3_MIN_DATA_CHUNK_SIZE 16384 2427 2428 /* The size in bytes of each chunk of data to read from the MP3 stream. minimp3 recommends at least 16K, but in an attempt to reduce data movement I'm making this slightly larger. */ 2429 #ifndef DRMP3_DATA_CHUNK_SIZE 2430 #define DRMP3_DATA_CHUNK_SIZE DRMP3_MIN_DATA_CHUNK_SIZE*4 2431 #endif 2432 2433 2434 #define DRMP3_COUNTOF(x) (sizeof(x) / sizeof(x[0])) 2435 #define DRMP3_CLAMP(x, lo, hi) (DRMP3_MAX(lo, DRMP3_MIN(x, hi))) 2436 2437 #ifndef DRMP3_PI_D 2438 #define DRMP3_PI_D 3.14159265358979323846264 2439 #endif 2440 2441 #define DRMP3_DEFAULT_RESAMPLER_LPF_ORDER 2 2442 2443 static DRMP3_INLINE float drmp3_mix_f32(float x, float y, float a) 2444 { 2445 return x*(1-a) + y*a; 2446 } 2447 static DRMP3_INLINE float drmp3_mix_f32_fast(float x, float y, float a) 2448 { 2449 float r0 = (y - x); 2450 float r1 = r0*a; 2451 return x + r1; 2452 /*return x + (y - x)*a;*/ 2453 } 2454 2455 2456 /* 2457 Greatest common factor using Euclid's algorithm iteratively. 2458 */ 2459 static DRMP3_INLINE drmp3_uint32 drmp3_gcf_u32(drmp3_uint32 a, drmp3_uint32 b) 2460 { 2461 for (;;) { 2462 if (b == 0) { 2463 break; 2464 } else { 2465 drmp3_uint32 t = a; 2466 a = b; 2467 b = t % a; 2468 } 2469 } 2470 2471 return a; 2472 } 2473 2474 2475 static DRMP3_INLINE double drmp3_sin(double x) 2476 { 2477 /* TODO: Implement custom sin(x). */ 2478 return sin(x); 2479 } 2480 2481 static DRMP3_INLINE double drmp3_exp(double x) 2482 { 2483 /* TODO: Implement custom exp(x). */ 2484 return exp(x); 2485 } 2486 2487 static DRMP3_INLINE double drmp3_cos(double x) 2488 { 2489 return drmp3_sin((DRMP3_PI_D*0.5) - x); 2490 } 2491 2492 2493 static void* drmp3__malloc_default(size_t sz, void* pUserData) 2494 { 2495 (void)pUserData; 2496 return DRMP3_MALLOC(sz); 2497 } 2498 2499 static void* drmp3__realloc_default(void* p, size_t sz, void* pUserData) 2500 { 2501 (void)pUserData; 2502 return DRMP3_REALLOC(p, sz); 2503 } 2504 2505 static void drmp3__free_default(void* p, void* pUserData) 2506 { 2507 (void)pUserData; 2508 DRMP3_FREE(p); 2509 } 2510 2511 2512 static void* drmp3__malloc_from_callbacks(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks) 2513 { 2514 if (pAllocationCallbacks == NULL) { 2515 return NULL; 2516 } 2517 2518 if (pAllocationCallbacks->onMalloc != NULL) { 2519 return pAllocationCallbacks->onMalloc(sz, pAllocationCallbacks->pUserData); 2520 } 2521 2522 /* Try using realloc(). */ 2523 if (pAllocationCallbacks->onRealloc != NULL) { 2524 return pAllocationCallbacks->onRealloc(NULL, sz, pAllocationCallbacks->pUserData); 2525 } 2526 2527 return NULL; 2528 } 2529 2530 static void* drmp3__realloc_from_callbacks(void* p, size_t szNew, size_t szOld, const drmp3_allocation_callbacks* pAllocationCallbacks) 2531 { 2532 if (pAllocationCallbacks == NULL) { 2533 return NULL; 2534 } 2535 2536 if (pAllocationCallbacks->onRealloc != NULL) { 2537 return pAllocationCallbacks->onRealloc(p, szNew, pAllocationCallbacks->pUserData); 2538 } 2539 2540 /* Try emulating realloc() in terms of malloc()/free(). */ 2541 if (pAllocationCallbacks->onMalloc != NULL && pAllocationCallbacks->onFree != NULL) { 2542 void* p2; 2543 2544 p2 = pAllocationCallbacks->onMalloc(szNew, pAllocationCallbacks->pUserData); 2545 if (p2 == NULL) { 2546 return NULL; 2547 } 2548 2549 if (p != NULL) { 2550 DRMP3_COPY_MEMORY(p2, p, szOld); 2551 pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); 2552 } 2553 2554 return p2; 2555 } 2556 2557 return NULL; 2558 } 2559 2560 static void drmp3__free_from_callbacks(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks) 2561 { 2562 if (p == NULL || pAllocationCallbacks == NULL) { 2563 return; 2564 } 2565 2566 if (pAllocationCallbacks->onFree != NULL) { 2567 pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); 2568 } 2569 } 2570 2571 2572 static drmp3_allocation_callbacks drmp3_copy_allocation_callbacks_or_defaults(const drmp3_allocation_callbacks* pAllocationCallbacks) 2573 { 2574 if (pAllocationCallbacks != NULL) { 2575 /* Copy. */ 2576 return *pAllocationCallbacks; 2577 } else { 2578 /* Defaults. */ 2579 drmp3_allocation_callbacks allocationCallbacks; 2580 allocationCallbacks.pUserData = NULL; 2581 allocationCallbacks.onMalloc = drmp3__malloc_default; 2582 allocationCallbacks.onRealloc = drmp3__realloc_default; 2583 allocationCallbacks.onFree = drmp3__free_default; 2584 return allocationCallbacks; 2585 } 2586 } 2587 2588 2589 2590 static size_t drmp3__on_read(drmp3* pMP3, void* pBufferOut, size_t bytesToRead) 2591 { 2592 size_t bytesRead = pMP3->onRead(pMP3->pUserData, pBufferOut, bytesToRead); 2593 pMP3->streamCursor += bytesRead; 2594 return bytesRead; 2595 } 2596 2597 static drmp3_bool32 drmp3__on_seek(drmp3* pMP3, int offset, drmp3_seek_origin origin) 2598 { 2599 DRMP3_ASSERT(offset >= 0); 2600 2601 if (!pMP3->onSeek(pMP3->pUserData, offset, origin)) { 2602 return DRMP3_FALSE; 2603 } 2604 2605 if (origin == drmp3_seek_origin_start) { 2606 pMP3->streamCursor = (drmp3_uint64)offset; 2607 } else { 2608 pMP3->streamCursor += offset; 2609 } 2610 2611 return DRMP3_TRUE; 2612 } 2613 2614 static drmp3_bool32 drmp3__on_seek_64(drmp3* pMP3, drmp3_uint64 offset, drmp3_seek_origin origin) 2615 { 2616 if (offset <= 0x7FFFFFFF) { 2617 return drmp3__on_seek(pMP3, (int)offset, origin); 2618 } 2619 2620 2621 /* Getting here "offset" is too large for a 32-bit integer. We just keep seeking forward until we hit the offset. */ 2622 if (!drmp3__on_seek(pMP3, 0x7FFFFFFF, drmp3_seek_origin_start)) { 2623 return DRMP3_FALSE; 2624 } 2625 2626 offset -= 0x7FFFFFFF; 2627 while (offset > 0) { 2628 if (offset <= 0x7FFFFFFF) { 2629 if (!drmp3__on_seek(pMP3, (int)offset, drmp3_seek_origin_current)) { 2630 return DRMP3_FALSE; 2631 } 2632 offset = 0; 2633 } else { 2634 if (!drmp3__on_seek(pMP3, 0x7FFFFFFF, drmp3_seek_origin_current)) { 2635 return DRMP3_FALSE; 2636 } 2637 offset -= 0x7FFFFFFF; 2638 } 2639 } 2640 2641 return DRMP3_TRUE; 2642 } 2643 2644 2645 static drmp3_uint32 drmp3_decode_next_frame_ex__callbacks(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) 2646 { 2647 drmp3_uint32 pcmFramesRead = 0; 2648 2649 DRMP3_ASSERT(pMP3 != NULL); 2650 DRMP3_ASSERT(pMP3->onRead != NULL); 2651 2652 if (pMP3->atEnd) { 2653 return 0; 2654 } 2655 2656 for (;;) { 2657 drmp3dec_frame_info info; 2658 2659 /* minimp3 recommends doing data submission in chunks of at least 16K. If we don't have at least 16K bytes available, get more. */ 2660 if (pMP3->dataSize < DRMP3_MIN_DATA_CHUNK_SIZE) { 2661 size_t bytesRead; 2662 2663 /* First we need to move the data down. */ 2664 if (pMP3->pData != NULL) { 2665 DRMP3_MOVE_MEMORY(pMP3->pData, pMP3->pData + pMP3->dataConsumed, pMP3->dataSize); 2666 } 2667 2668 pMP3->dataConsumed = 0; 2669 2670 if (pMP3->dataCapacity < DRMP3_DATA_CHUNK_SIZE) { 2671 drmp3_uint8* pNewData; 2672 size_t newDataCap; 2673 2674 newDataCap = DRMP3_DATA_CHUNK_SIZE; 2675 2676 pNewData = (drmp3_uint8*)drmp3__realloc_from_callbacks(pMP3->pData, newDataCap, pMP3->dataCapacity, &pMP3->allocationCallbacks); 2677 if (pNewData == NULL) { 2678 return 0; /* Out of memory. */ 2679 } 2680 2681 pMP3->pData = pNewData; 2682 pMP3->dataCapacity = newDataCap; 2683 } 2684 2685 bytesRead = drmp3__on_read(pMP3, pMP3->pData + pMP3->dataSize, (pMP3->dataCapacity - pMP3->dataSize)); 2686 if (bytesRead == 0) { 2687 if (pMP3->dataSize == 0) { 2688 pMP3->atEnd = DRMP3_TRUE; 2689 return 0; /* No data. */ 2690 } 2691 } 2692 2693 pMP3->dataSize += bytesRead; 2694 } 2695 2696 if (pMP3->dataSize > INT_MAX) { 2697 pMP3->atEnd = DRMP3_TRUE; 2698 return 0; /* File too big. */ 2699 } 2700 2701 DRMP3_ASSERT(pMP3->pData != NULL); 2702 DRMP3_ASSERT(pMP3->dataCapacity > 0); 2703 2704 pcmFramesRead = drmp3dec_decode_frame(&pMP3->decoder, pMP3->pData + pMP3->dataConsumed, (int)pMP3->dataSize, pPCMFrames, &info); /* <-- Safe size_t -> int conversion thanks to the check above. */ 2705 2706 /* Consume the data. */ 2707 if (info.frame_bytes > 0) { 2708 pMP3->dataConsumed += (size_t)info.frame_bytes; 2709 pMP3->dataSize -= (size_t)info.frame_bytes; 2710 } 2711 2712 /* pcmFramesRead will be equal to 0 if decoding failed. If it is zero and info.frame_bytes > 0 then we have successfully decoded the frame. */ 2713 if (pcmFramesRead > 0) { 2714 pcmFramesRead = drmp3_hdr_frame_samples(pMP3->decoder.header); 2715 pMP3->pcmFramesConsumedInMP3Frame = 0; 2716 pMP3->pcmFramesRemainingInMP3Frame = pcmFramesRead; 2717 pMP3->mp3FrameChannels = info.channels; 2718 pMP3->mp3FrameSampleRate = info.hz; 2719 break; 2720 } else if (info.frame_bytes == 0) { 2721 /* Need more data. minimp3 recommends doing data submission in 16K chunks. */ 2722 size_t bytesRead; 2723 2724 /* First we need to move the data down. */ 2725 DRMP3_MOVE_MEMORY(pMP3->pData, pMP3->pData + pMP3->dataConsumed, pMP3->dataSize); 2726 pMP3->dataConsumed = 0; 2727 2728 if (pMP3->dataCapacity == pMP3->dataSize) { 2729 /* No room. Expand. */ 2730 drmp3_uint8* pNewData; 2731 size_t newDataCap; 2732 2733 newDataCap = pMP3->dataCapacity + DRMP3_DATA_CHUNK_SIZE; 2734 2735 pNewData = (drmp3_uint8*)drmp3__realloc_from_callbacks(pMP3->pData, newDataCap, pMP3->dataCapacity, &pMP3->allocationCallbacks); 2736 if (pNewData == NULL) { 2737 return 0; /* Out of memory. */ 2738 } 2739 2740 pMP3->pData = pNewData; 2741 pMP3->dataCapacity = newDataCap; 2742 } 2743 2744 /* Fill in a chunk. */ 2745 bytesRead = drmp3__on_read(pMP3, pMP3->pData + pMP3->dataSize, (pMP3->dataCapacity - pMP3->dataSize)); 2746 if (bytesRead == 0) { 2747 pMP3->atEnd = DRMP3_TRUE; 2748 return 0; /* Error reading more data. */ 2749 } 2750 2751 pMP3->dataSize += bytesRead; 2752 } 2753 }; 2754 2755 return pcmFramesRead; 2756 } 2757 2758 static drmp3_uint32 drmp3_decode_next_frame_ex__memory(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) 2759 { 2760 drmp3_uint32 pcmFramesRead = 0; 2761 drmp3dec_frame_info info; 2762 2763 DRMP3_ASSERT(pMP3 != NULL); 2764 DRMP3_ASSERT(pMP3->memory.pData != NULL); 2765 2766 if (pMP3->atEnd) { 2767 return 0; 2768 } 2769 2770 for (;;) { 2771 pcmFramesRead = drmp3dec_decode_frame(&pMP3->decoder, pMP3->memory.pData + pMP3->memory.currentReadPos, (int)(pMP3->memory.dataSize - pMP3->memory.currentReadPos), pPCMFrames, &info); 2772 if (pcmFramesRead > 0) { 2773 pcmFramesRead = drmp3_hdr_frame_samples(pMP3->decoder.header); 2774 pMP3->pcmFramesConsumedInMP3Frame = 0; 2775 pMP3->pcmFramesRemainingInMP3Frame = pcmFramesRead; 2776 pMP3->mp3FrameChannels = info.channels; 2777 pMP3->mp3FrameSampleRate = info.hz; 2778 break; 2779 } else if (info.frame_bytes > 0) { 2780 /* No frames were read, but it looks like we skipped past one. Read the next MP3 frame. */ 2781 pMP3->memory.currentReadPos += (size_t)info.frame_bytes; 2782 } else { 2783 /* Nothing at all was read. Abort. */ 2784 break; 2785 } 2786 } 2787 2788 /* Consume the data. */ 2789 pMP3->memory.currentReadPos += (size_t)info.frame_bytes; 2790 2791 return pcmFramesRead; 2792 } 2793 2794 static drmp3_uint32 drmp3_decode_next_frame_ex(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) 2795 { 2796 if (pMP3->memory.pData != NULL && pMP3->memory.dataSize > 0) { 2797 return drmp3_decode_next_frame_ex__memory(pMP3, pPCMFrames); 2798 } else { 2799 return drmp3_decode_next_frame_ex__callbacks(pMP3, pPCMFrames); 2800 } 2801 } 2802 2803 static drmp3_uint32 drmp3_decode_next_frame(drmp3* pMP3) 2804 { 2805 DRMP3_ASSERT(pMP3 != NULL); 2806 return drmp3_decode_next_frame_ex(pMP3, (drmp3d_sample_t*)pMP3->pcmFrames); 2807 } 2808 2809 #if 0 2810 static drmp3_uint32 drmp3_seek_next_frame(drmp3* pMP3) 2811 { 2812 drmp3_uint32 pcmFrameCount; 2813 2814 DRMP3_ASSERT(pMP3 != NULL); 2815 2816 pcmFrameCount = drmp3_decode_next_frame_ex(pMP3, NULL); 2817 if (pcmFrameCount == 0) { 2818 return 0; 2819 } 2820 2821 /* We have essentially just skipped past the frame, so just set the remaining samples to 0. */ 2822 pMP3->currentPCMFrame += pcmFrameCount; 2823 pMP3->pcmFramesConsumedInMP3Frame = pcmFrameCount; 2824 pMP3->pcmFramesRemainingInMP3Frame = 0; 2825 2826 return pcmFrameCount; 2827 } 2828 #endif 2829 2830 static drmp3_bool32 drmp3_init_internal(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks) 2831 { 2832 DRMP3_ASSERT(pMP3 != NULL); 2833 DRMP3_ASSERT(onRead != NULL); 2834 2835 /* This function assumes the output object has already been reset to 0. Do not do that here, otherwise things will break. */ 2836 drmp3dec_init(&pMP3->decoder); 2837 2838 pMP3->onRead = onRead; 2839 pMP3->onSeek = onSeek; 2840 pMP3->pUserData = pUserData; 2841 pMP3->allocationCallbacks = drmp3_copy_allocation_callbacks_or_defaults(pAllocationCallbacks); 2842 2843 if (pMP3->allocationCallbacks.onFree == NULL || (pMP3->allocationCallbacks.onMalloc == NULL && pMP3->allocationCallbacks.onRealloc == NULL)) { 2844 return DRMP3_FALSE; /* Invalid allocation callbacks. */ 2845 } 2846 2847 /* Decode the first frame to confirm that it is indeed a valid MP3 stream. */ 2848 if (drmp3_decode_next_frame(pMP3) == 0) { 2849 drmp3__free_from_callbacks(pMP3->pData, &pMP3->allocationCallbacks); /* The call above may have allocated memory. Need to make sure it's freed before aborting. */ 2850 return DRMP3_FALSE; /* Not a valid MP3 stream. */ 2851 } 2852 2853 pMP3->channels = pMP3->mp3FrameChannels; 2854 pMP3->sampleRate = pMP3->mp3FrameSampleRate; 2855 2856 return DRMP3_TRUE; 2857 } 2858 2859 DRMP3_API drmp3_bool32 drmp3_init(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks) 2860 { 2861 if (pMP3 == NULL || onRead == NULL) { 2862 return DRMP3_FALSE; 2863 } 2864 2865 DRMP3_ZERO_OBJECT(pMP3); 2866 return drmp3_init_internal(pMP3, onRead, onSeek, pUserData, pAllocationCallbacks); 2867 } 2868 2869 2870 static size_t drmp3__on_read_memory(void* pUserData, void* pBufferOut, size_t bytesToRead) 2871 { 2872 drmp3* pMP3 = (drmp3*)pUserData; 2873 size_t bytesRemaining; 2874 2875 DRMP3_ASSERT(pMP3 != NULL); 2876 DRMP3_ASSERT(pMP3->memory.dataSize >= pMP3->memory.currentReadPos); 2877 2878 bytesRemaining = pMP3->memory.dataSize - pMP3->memory.currentReadPos; 2879 if (bytesToRead > bytesRemaining) { 2880 bytesToRead = bytesRemaining; 2881 } 2882 2883 if (bytesToRead > 0) { 2884 DRMP3_COPY_MEMORY(pBufferOut, pMP3->memory.pData + pMP3->memory.currentReadPos, bytesToRead); 2885 pMP3->memory.currentReadPos += bytesToRead; 2886 } 2887 2888 return bytesToRead; 2889 } 2890 2891 static drmp3_bool32 drmp3__on_seek_memory(void* pUserData, int byteOffset, drmp3_seek_origin origin) 2892 { 2893 drmp3* pMP3 = (drmp3*)pUserData; 2894 2895 DRMP3_ASSERT(pMP3 != NULL); 2896 2897 if (origin == drmp3_seek_origin_current) { 2898 if (byteOffset > 0) { 2899 if (pMP3->memory.currentReadPos + byteOffset > pMP3->memory.dataSize) { 2900 byteOffset = (int)(pMP3->memory.dataSize - pMP3->memory.currentReadPos); /* Trying to seek too far forward. */ 2901 } 2902 } else { 2903 if (pMP3->memory.currentReadPos < (size_t)-byteOffset) { 2904 byteOffset = -(int)pMP3->memory.currentReadPos; /* Trying to seek too far backwards. */ 2905 } 2906 } 2907 2908 /* This will never underflow thanks to the clamps above. */ 2909 pMP3->memory.currentReadPos += byteOffset; 2910 } else { 2911 if ((drmp3_uint32)byteOffset <= pMP3->memory.dataSize) { 2912 pMP3->memory.currentReadPos = byteOffset; 2913 } else { 2914 pMP3->memory.currentReadPos = pMP3->memory.dataSize; /* Trying to seek too far forward. */ 2915 } 2916 } 2917 2918 return DRMP3_TRUE; 2919 } 2920 2921 DRMP3_API drmp3_bool32 drmp3_init_memory(drmp3* pMP3, const void* pData, size_t dataSize, const drmp3_allocation_callbacks* pAllocationCallbacks) 2922 { 2923 if (pMP3 == NULL) { 2924 return DRMP3_FALSE; 2925 } 2926 2927 DRMP3_ZERO_OBJECT(pMP3); 2928 2929 if (pData == NULL || dataSize == 0) { 2930 return DRMP3_FALSE; 2931 } 2932 2933 pMP3->memory.pData = (const drmp3_uint8*)pData; 2934 pMP3->memory.dataSize = dataSize; 2935 pMP3->memory.currentReadPos = 0; 2936 2937 return drmp3_init_internal(pMP3, drmp3__on_read_memory, drmp3__on_seek_memory, pMP3, pAllocationCallbacks); 2938 } 2939 2940 2941 #ifndef DR_MP3_NO_STDIO 2942 #include <stdio.h> 2943 #include <wchar.h> /* For wcslen(), wcsrtombs() */ 2944 2945 /* drmp3_result_from_errno() is only used inside DR_MP3_NO_STDIO for now. Move this out if it's ever used elsewhere. */ 2946 #include <errno.h> 2947 static drmp3_result drmp3_result_from_errno(int e) 2948 { 2949 switch (e) 2950 { 2951 case 0: return DRMP3_SUCCESS; 2952 #ifdef EPERM 2953 case EPERM: return DRMP3_INVALID_OPERATION; 2954 #endif 2955 #ifdef ENOENT 2956 case ENOENT: return DRMP3_DOES_NOT_EXIST; 2957 #endif 2958 #ifdef ESRCH 2959 case ESRCH: return DRMP3_DOES_NOT_EXIST; 2960 #endif 2961 #ifdef EINTR 2962 case EINTR: return DRMP3_INTERRUPT; 2963 #endif 2964 #ifdef EIO 2965 case EIO: return DRMP3_IO_ERROR; 2966 #endif 2967 #ifdef ENXIO 2968 case ENXIO: return DRMP3_DOES_NOT_EXIST; 2969 #endif 2970 #ifdef E2BIG 2971 case E2BIG: return DRMP3_INVALID_ARGS; 2972 #endif 2973 #ifdef ENOEXEC 2974 case ENOEXEC: return DRMP3_INVALID_FILE; 2975 #endif 2976 #ifdef EBADF 2977 case EBADF: return DRMP3_INVALID_FILE; 2978 #endif 2979 #ifdef ECHILD 2980 case ECHILD: return DRMP3_ERROR; 2981 #endif 2982 #ifdef EAGAIN 2983 case EAGAIN: return DRMP3_UNAVAILABLE; 2984 #endif 2985 #ifdef ENOMEM 2986 case ENOMEM: return DRMP3_OUT_OF_MEMORY; 2987 #endif 2988 #ifdef EACCES 2989 case EACCES: return DRMP3_ACCESS_DENIED; 2990 #endif 2991 #ifdef EFAULT 2992 case EFAULT: return DRMP3_BAD_ADDRESS; 2993 #endif 2994 #ifdef ENOTBLK 2995 case ENOTBLK: return DRMP3_ERROR; 2996 #endif 2997 #ifdef EBUSY 2998 case EBUSY: return DRMP3_BUSY; 2999 #endif 3000 #ifdef EEXIST 3001 case EEXIST: return DRMP3_ALREADY_EXISTS; 3002 #endif 3003 #ifdef EXDEV 3004 case EXDEV: return DRMP3_ERROR; 3005 #endif 3006 #ifdef ENODEV 3007 case ENODEV: return DRMP3_DOES_NOT_EXIST; 3008 #endif 3009 #ifdef ENOTDIR 3010 case ENOTDIR: return DRMP3_NOT_DIRECTORY; 3011 #endif 3012 #ifdef EISDIR 3013 case EISDIR: return DRMP3_IS_DIRECTORY; 3014 #endif 3015 #ifdef EINVAL 3016 case EINVAL: return DRMP3_INVALID_ARGS; 3017 #endif 3018 #ifdef ENFILE 3019 case ENFILE: return DRMP3_TOO_MANY_OPEN_FILES; 3020 #endif 3021 #ifdef EMFILE 3022 case EMFILE: return DRMP3_TOO_MANY_OPEN_FILES; 3023 #endif 3024 #ifdef ENOTTY 3025 case ENOTTY: return DRMP3_INVALID_OPERATION; 3026 #endif 3027 #ifdef ETXTBSY 3028 case ETXTBSY: return DRMP3_BUSY; 3029 #endif 3030 #ifdef EFBIG 3031 case EFBIG: return DRMP3_TOO_BIG; 3032 #endif 3033 #ifdef ENOSPC 3034 case ENOSPC: return DRMP3_NO_SPACE; 3035 #endif 3036 #ifdef ESPIPE 3037 case ESPIPE: return DRMP3_BAD_SEEK; 3038 #endif 3039 #ifdef EROFS 3040 case EROFS: return DRMP3_ACCESS_DENIED; 3041 #endif 3042 #ifdef EMLINK 3043 case EMLINK: return DRMP3_TOO_MANY_LINKS; 3044 #endif 3045 #ifdef EPIPE 3046 case EPIPE: return DRMP3_BAD_PIPE; 3047 #endif 3048 #ifdef EDOM 3049 case EDOM: return DRMP3_OUT_OF_RANGE; 3050 #endif 3051 #ifdef ERANGE 3052 case ERANGE: return DRMP3_OUT_OF_RANGE; 3053 #endif 3054 #ifdef EDEADLK 3055 case EDEADLK: return DRMP3_DEADLOCK; 3056 #endif 3057 #ifdef ENAMETOOLONG 3058 case ENAMETOOLONG: return DRMP3_PATH_TOO_LONG; 3059 #endif 3060 #ifdef ENOLCK 3061 case ENOLCK: return DRMP3_ERROR; 3062 #endif 3063 #ifdef ENOSYS 3064 case ENOSYS: return DRMP3_NOT_IMPLEMENTED; 3065 #endif 3066 #ifdef ENOTEMPTY 3067 case ENOTEMPTY: return DRMP3_DIRECTORY_NOT_EMPTY; 3068 #endif 3069 #ifdef ELOOP 3070 case ELOOP: return DRMP3_TOO_MANY_LINKS; 3071 #endif 3072 #ifdef ENOMSG 3073 case ENOMSG: return DRMP3_NO_MESSAGE; 3074 #endif 3075 #ifdef EIDRM 3076 case EIDRM: return DRMP3_ERROR; 3077 #endif 3078 #ifdef ECHRNG 3079 case ECHRNG: return DRMP3_ERROR; 3080 #endif 3081 #ifdef EL2NSYNC 3082 case EL2NSYNC: return DRMP3_ERROR; 3083 #endif 3084 #ifdef EL3HLT 3085 case EL3HLT: return DRMP3_ERROR; 3086 #endif 3087 #ifdef EL3RST 3088 case EL3RST: return DRMP3_ERROR; 3089 #endif 3090 #ifdef ELNRNG 3091 case ELNRNG: return DRMP3_OUT_OF_RANGE; 3092 #endif 3093 #ifdef EUNATCH 3094 case EUNATCH: return DRMP3_ERROR; 3095 #endif 3096 #ifdef ENOCSI 3097 case ENOCSI: return DRMP3_ERROR; 3098 #endif 3099 #ifdef EL2HLT 3100 case EL2HLT: return DRMP3_ERROR; 3101 #endif 3102 #ifdef EBADE 3103 case EBADE: return DRMP3_ERROR; 3104 #endif 3105 #ifdef EBADR 3106 case EBADR: return DRMP3_ERROR; 3107 #endif 3108 #ifdef EXFULL 3109 case EXFULL: return DRMP3_ERROR; 3110 #endif 3111 #ifdef ENOANO 3112 case ENOANO: return DRMP3_ERROR; 3113 #endif 3114 #ifdef EBADRQC 3115 case EBADRQC: return DRMP3_ERROR; 3116 #endif 3117 #ifdef EBADSLT 3118 case EBADSLT: return DRMP3_ERROR; 3119 #endif 3120 #ifdef EBFONT 3121 case EBFONT: return DRMP3_INVALID_FILE; 3122 #endif 3123 #ifdef ENOSTR 3124 case ENOSTR: return DRMP3_ERROR; 3125 #endif 3126 #ifdef ENODATA 3127 case ENODATA: return DRMP3_NO_DATA_AVAILABLE; 3128 #endif 3129 #ifdef ETIME 3130 case ETIME: return DRMP3_TIMEOUT; 3131 #endif 3132 #ifdef ENOSR 3133 case ENOSR: return DRMP3_NO_DATA_AVAILABLE; 3134 #endif 3135 #ifdef ENONET 3136 case ENONET: return DRMP3_NO_NETWORK; 3137 #endif 3138 #ifdef ENOPKG 3139 case ENOPKG: return DRMP3_ERROR; 3140 #endif 3141 #ifdef EREMOTE 3142 case EREMOTE: return DRMP3_ERROR; 3143 #endif 3144 #ifdef ENOLINK 3145 case ENOLINK: return DRMP3_ERROR; 3146 #endif 3147 #ifdef EADV 3148 case EADV: return DRMP3_ERROR; 3149 #endif 3150 #ifdef ESRMNT 3151 case ESRMNT: return DRMP3_ERROR; 3152 #endif 3153 #ifdef ECOMM 3154 case ECOMM: return DRMP3_ERROR; 3155 #endif 3156 #ifdef EPROTO 3157 case EPROTO: return DRMP3_ERROR; 3158 #endif 3159 #ifdef EMULTIHOP 3160 case EMULTIHOP: return DRMP3_ERROR; 3161 #endif 3162 #ifdef EDOTDOT 3163 case EDOTDOT: return DRMP3_ERROR; 3164 #endif 3165 #ifdef EBADMSG 3166 case EBADMSG: return DRMP3_BAD_MESSAGE; 3167 #endif 3168 #ifdef EOVERFLOW 3169 case EOVERFLOW: return DRMP3_TOO_BIG; 3170 #endif 3171 #ifdef ENOTUNIQ 3172 case ENOTUNIQ: return DRMP3_NOT_UNIQUE; 3173 #endif 3174 #ifdef EBADFD 3175 case EBADFD: return DRMP3_ERROR; 3176 #endif 3177 #ifdef EREMCHG 3178 case EREMCHG: return DRMP3_ERROR; 3179 #endif 3180 #ifdef ELIBACC 3181 case ELIBACC: return DRMP3_ACCESS_DENIED; 3182 #endif 3183 #ifdef ELIBBAD 3184 case ELIBBAD: return DRMP3_INVALID_FILE; 3185 #endif 3186 #ifdef ELIBSCN 3187 case ELIBSCN: return DRMP3_INVALID_FILE; 3188 #endif 3189 #ifdef ELIBMAX 3190 case ELIBMAX: return DRMP3_ERROR; 3191 #endif 3192 #ifdef ELIBEXEC 3193 case ELIBEXEC: return DRMP3_ERROR; 3194 #endif 3195 #ifdef EILSEQ 3196 case EILSEQ: return DRMP3_INVALID_DATA; 3197 #endif 3198 #ifdef ERESTART 3199 case ERESTART: return DRMP3_ERROR; 3200 #endif 3201 #ifdef ESTRPIPE 3202 case ESTRPIPE: return DRMP3_ERROR; 3203 #endif 3204 #ifdef EUSERS 3205 case EUSERS: return DRMP3_ERROR; 3206 #endif 3207 #ifdef ENOTSOCK 3208 case ENOTSOCK: return DRMP3_NOT_SOCKET; 3209 #endif 3210 #ifdef EDESTADDRREQ 3211 case EDESTADDRREQ: return DRMP3_NO_ADDRESS; 3212 #endif 3213 #ifdef EMSGSIZE 3214 case EMSGSIZE: return DRMP3_TOO_BIG; 3215 #endif 3216 #ifdef EPROTOTYPE 3217 case EPROTOTYPE: return DRMP3_BAD_PROTOCOL; 3218 #endif 3219 #ifdef ENOPROTOOPT 3220 case ENOPROTOOPT: return DRMP3_PROTOCOL_UNAVAILABLE; 3221 #endif 3222 #ifdef EPROTONOSUPPORT 3223 case EPROTONOSUPPORT: return DRMP3_PROTOCOL_NOT_SUPPORTED; 3224 #endif 3225 #ifdef ESOCKTNOSUPPORT 3226 case ESOCKTNOSUPPORT: return DRMP3_SOCKET_NOT_SUPPORTED; 3227 #endif 3228 #ifdef EOPNOTSUPP 3229 case EOPNOTSUPP: return DRMP3_INVALID_OPERATION; 3230 #endif 3231 #ifdef EPFNOSUPPORT 3232 case EPFNOSUPPORT: return DRMP3_PROTOCOL_FAMILY_NOT_SUPPORTED; 3233 #endif 3234 #ifdef EAFNOSUPPORT 3235 case EAFNOSUPPORT: return DRMP3_ADDRESS_FAMILY_NOT_SUPPORTED; 3236 #endif 3237 #ifdef EADDRINUSE 3238 case EADDRINUSE: return DRMP3_ALREADY_IN_USE; 3239 #endif 3240 #ifdef EADDRNOTAVAIL 3241 case EADDRNOTAVAIL: return DRMP3_ERROR; 3242 #endif 3243 #ifdef ENETDOWN 3244 case ENETDOWN: return DRMP3_NO_NETWORK; 3245 #endif 3246 #ifdef ENETUNREACH 3247 case ENETUNREACH: return DRMP3_NO_NETWORK; 3248 #endif 3249 #ifdef ENETRESET 3250 case ENETRESET: return DRMP3_NO_NETWORK; 3251 #endif 3252 #ifdef ECONNABORTED 3253 case ECONNABORTED: return DRMP3_NO_NETWORK; 3254 #endif 3255 #ifdef ECONNRESET 3256 case ECONNRESET: return DRMP3_CONNECTION_RESET; 3257 #endif 3258 #ifdef ENOBUFS 3259 case ENOBUFS: return DRMP3_NO_SPACE; 3260 #endif 3261 #ifdef EISCONN 3262 case EISCONN: return DRMP3_ALREADY_CONNECTED; 3263 #endif 3264 #ifdef ENOTCONN 3265 case ENOTCONN: return DRMP3_NOT_CONNECTED; 3266 #endif 3267 #ifdef ESHUTDOWN 3268 case ESHUTDOWN: return DRMP3_ERROR; 3269 #endif 3270 #ifdef ETOOMANYREFS 3271 case ETOOMANYREFS: return DRMP3_ERROR; 3272 #endif 3273 #ifdef ETIMEDOUT 3274 case ETIMEDOUT: return DRMP3_TIMEOUT; 3275 #endif 3276 #ifdef ECONNREFUSED 3277 case ECONNREFUSED: return DRMP3_CONNECTION_REFUSED; 3278 #endif 3279 #ifdef EHOSTDOWN 3280 case EHOSTDOWN: return DRMP3_NO_HOST; 3281 #endif 3282 #ifdef EHOSTUNREACH 3283 case EHOSTUNREACH: return DRMP3_NO_HOST; 3284 #endif 3285 #ifdef EALREADY 3286 case EALREADY: return DRMP3_IN_PROGRESS; 3287 #endif 3288 #ifdef EINPROGRESS 3289 case EINPROGRESS: return DRMP3_IN_PROGRESS; 3290 #endif 3291 #ifdef ESTALE 3292 case ESTALE: return DRMP3_INVALID_FILE; 3293 #endif 3294 #ifdef EUCLEAN 3295 case EUCLEAN: return DRMP3_ERROR; 3296 #endif 3297 #ifdef ENOTNAM 3298 case ENOTNAM: return DRMP3_ERROR; 3299 #endif 3300 #ifdef ENAVAIL 3301 case ENAVAIL: return DRMP3_ERROR; 3302 #endif 3303 #ifdef EISNAM 3304 case EISNAM: return DRMP3_ERROR; 3305 #endif 3306 #ifdef EREMOTEIO 3307 case EREMOTEIO: return DRMP3_IO_ERROR; 3308 #endif 3309 #ifdef EDQUOT 3310 case EDQUOT: return DRMP3_NO_SPACE; 3311 #endif 3312 #ifdef ENOMEDIUM 3313 case ENOMEDIUM: return DRMP3_DOES_NOT_EXIST; 3314 #endif 3315 #ifdef EMEDIUMTYPE 3316 case EMEDIUMTYPE: return DRMP3_ERROR; 3317 #endif 3318 #ifdef ECANCELED 3319 case ECANCELED: return DRMP3_CANCELLED; 3320 #endif 3321 #ifdef ENOKEY 3322 case ENOKEY: return DRMP3_ERROR; 3323 #endif 3324 #ifdef EKEYEXPIRED 3325 case EKEYEXPIRED: return DRMP3_ERROR; 3326 #endif 3327 #ifdef EKEYREVOKED 3328 case EKEYREVOKED: return DRMP3_ERROR; 3329 #endif 3330 #ifdef EKEYREJECTED 3331 case EKEYREJECTED: return DRMP3_ERROR; 3332 #endif 3333 #ifdef EOWNERDEAD 3334 case EOWNERDEAD: return DRMP3_ERROR; 3335 #endif 3336 #ifdef ENOTRECOVERABLE 3337 case ENOTRECOVERABLE: return DRMP3_ERROR; 3338 #endif 3339 #ifdef ERFKILL 3340 case ERFKILL: return DRMP3_ERROR; 3341 #endif 3342 #ifdef EHWPOISON 3343 case EHWPOISON: return DRMP3_ERROR; 3344 #endif 3345 default: return DRMP3_ERROR; 3346 } 3347 } 3348 3349 static drmp3_result drmp3_fopen(FILE** ppFile, const char* pFilePath, const char* pOpenMode) 3350 { 3351 #if defined(_MSC_VER) && _MSC_VER >= 1400 3352 errno_t err; 3353 #endif 3354 3355 if (ppFile != NULL) { 3356 *ppFile = NULL; /* Safety. */ 3357 } 3358 3359 if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { 3360 return DRMP3_INVALID_ARGS; 3361 } 3362 3363 #if defined(_MSC_VER) && _MSC_VER >= 1400 3364 err = fopen_s(ppFile, pFilePath, pOpenMode); 3365 if (err != 0) { 3366 return drmp3_result_from_errno(err); 3367 } 3368 #else 3369 #if defined(_WIN32) || defined(__APPLE__) 3370 *ppFile = fopen(pFilePath, pOpenMode); 3371 #else 3372 #if defined(_FILE_OFFSET_BITS) && _FILE_OFFSET_BITS == 64 && defined(_LARGEFILE64_SOURCE) 3373 *ppFile = fopen64(pFilePath, pOpenMode); 3374 #else 3375 *ppFile = fopen(pFilePath, pOpenMode); 3376 #endif 3377 #endif 3378 if (*ppFile == NULL) { 3379 drmp3_result result = drmp3_result_from_errno(errno); 3380 if (result == DRMP3_SUCCESS) { 3381 result = DRMP3_ERROR; /* Just a safety check to make sure we never ever return success when pFile == NULL. */ 3382 } 3383 3384 return result; 3385 } 3386 #endif 3387 3388 return DRMP3_SUCCESS; 3389 } 3390 3391 /* 3392 _wfopen() isn't always available in all compilation environments. 3393 3394 * Windows only. 3395 * MSVC seems to support it universally as far back as VC6 from what I can tell (haven't checked further back). 3396 * MinGW-64 (both 32- and 64-bit) seems to support it. 3397 * MinGW wraps it in !defined(__STRICT_ANSI__). 3398 * OpenWatcom wraps it in !defined(_NO_EXT_KEYS). 3399 3400 This can be reviewed as compatibility issues arise. The preference is to use _wfopen_s() and _wfopen() as opposed to the wcsrtombs() 3401 fallback, so if you notice your compiler not detecting this properly I'm happy to look at adding support. 3402 */ 3403 #if defined(_WIN32) 3404 #if defined(_MSC_VER) || defined(__MINGW64__) || (!defined(__STRICT_ANSI__) && !defined(_NO_EXT_KEYS)) 3405 #define DRMP3_HAS_WFOPEN 3406 #endif 3407 #endif 3408 3409 static drmp3_result drmp3_wfopen(FILE** ppFile, const wchar_t* pFilePath, const wchar_t* pOpenMode, const drmp3_allocation_callbacks* pAllocationCallbacks) 3410 { 3411 if (ppFile != NULL) { 3412 *ppFile = NULL; /* Safety. */ 3413 } 3414 3415 if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { 3416 return DRMP3_INVALID_ARGS; 3417 } 3418 3419 #if defined(DRMP3_HAS_WFOPEN) 3420 { 3421 /* Use _wfopen() on Windows. */ 3422 #if defined(_MSC_VER) && _MSC_VER >= 1400 3423 errno_t err = _wfopen_s(ppFile, pFilePath, pOpenMode); 3424 if (err != 0) { 3425 return drmp3_result_from_errno(err); 3426 } 3427 #else 3428 *ppFile = _wfopen(pFilePath, pOpenMode); 3429 if (*ppFile == NULL) { 3430 return drmp3_result_from_errno(errno); 3431 } 3432 #endif 3433 (void)pAllocationCallbacks; 3434 } 3435 #else 3436 /* 3437 Use fopen() on anything other than Windows. Requires a conversion. This is annoying because fopen() is locale specific. The only real way I can 3438 think of to do this is with wcsrtombs(). Note that wcstombs() is apparently not thread-safe because it uses a static global mbstate_t object for 3439 maintaining state. I've checked this with -std=c89 and it works, but if somebody get's a compiler error I'll look into improving compatibility. 3440 */ 3441 { 3442 mbstate_t mbs; 3443 size_t lenMB; 3444 const wchar_t* pFilePathTemp = pFilePath; 3445 char* pFilePathMB = NULL; 3446 char pOpenModeMB[32] = {0}; 3447 3448 /* Get the length first. */ 3449 DRMP3_ZERO_OBJECT(&mbs); 3450 lenMB = wcsrtombs(NULL, &pFilePathTemp, 0, &mbs); 3451 if (lenMB == (size_t)-1) { 3452 return drmp3_result_from_errno(errno); 3453 } 3454 3455 pFilePathMB = (char*)drmp3__malloc_from_callbacks(lenMB + 1, pAllocationCallbacks); 3456 if (pFilePathMB == NULL) { 3457 return DRMP3_OUT_OF_MEMORY; 3458 } 3459 3460 pFilePathTemp = pFilePath; 3461 DRMP3_ZERO_OBJECT(&mbs); 3462 wcsrtombs(pFilePathMB, &pFilePathTemp, lenMB + 1, &mbs); 3463 3464 /* The open mode should always consist of ASCII characters so we should be able to do a trivial conversion. */ 3465 { 3466 size_t i = 0; 3467 for (;;) { 3468 if (pOpenMode[i] == 0) { 3469 pOpenModeMB[i] = '\0'; 3470 break; 3471 } 3472 3473 pOpenModeMB[i] = (char)pOpenMode[i]; 3474 i += 1; 3475 } 3476 } 3477 3478 *ppFile = fopen(pFilePathMB, pOpenModeMB); 3479 3480 drmp3__free_from_callbacks(pFilePathMB, pAllocationCallbacks); 3481 } 3482 3483 if (*ppFile == NULL) { 3484 return DRMP3_ERROR; 3485 } 3486 #endif 3487 3488 return DRMP3_SUCCESS; 3489 } 3490 3491 3492 3493 static size_t drmp3__on_read_stdio(void* pUserData, void* pBufferOut, size_t bytesToRead) 3494 { 3495 return fread(pBufferOut, 1, bytesToRead, (FILE*)pUserData); 3496 } 3497 3498 static drmp3_bool32 drmp3__on_seek_stdio(void* pUserData, int offset, drmp3_seek_origin origin) 3499 { 3500 return fseek((FILE*)pUserData, offset, (origin == drmp3_seek_origin_current) ? SEEK_CUR : SEEK_SET) == 0; 3501 } 3502 3503 DRMP3_API drmp3_bool32 drmp3_init_file(drmp3* pMP3, const char* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks) 3504 { 3505 drmp3_bool32 result; 3506 FILE* pFile; 3507 3508 if (drmp3_fopen(&pFile, pFilePath, "rb") != DRMP3_SUCCESS) { 3509 return DRMP3_FALSE; 3510 } 3511 3512 result = drmp3_init(pMP3, drmp3__on_read_stdio, drmp3__on_seek_stdio, (void*)pFile, pAllocationCallbacks); 3513 if (result != DRMP3_TRUE) { 3514 fclose(pFile); 3515 return result; 3516 } 3517 3518 return DRMP3_TRUE; 3519 } 3520 3521 DRMP3_API drmp3_bool32 drmp3_init_file_w(drmp3* pMP3, const wchar_t* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks) 3522 { 3523 drmp3_bool32 result; 3524 FILE* pFile; 3525 3526 if (drmp3_wfopen(&pFile, pFilePath, L"rb", pAllocationCallbacks) != DRMP3_SUCCESS) { 3527 return DRMP3_FALSE; 3528 } 3529 3530 result = drmp3_init(pMP3, drmp3__on_read_stdio, drmp3__on_seek_stdio, (void*)pFile, pAllocationCallbacks); 3531 if (result != DRMP3_TRUE) { 3532 fclose(pFile); 3533 return result; 3534 } 3535 3536 return DRMP3_TRUE; 3537 } 3538 #endif 3539 3540 DRMP3_API void drmp3_uninit(drmp3* pMP3) 3541 { 3542 if (pMP3 == NULL) { 3543 return; 3544 } 3545 3546 #ifndef DR_MP3_NO_STDIO 3547 if (pMP3->onRead == drmp3__on_read_stdio) { 3548 FILE* pFile = (FILE*)pMP3->pUserData; 3549 if (pFile != NULL) { 3550 fclose(pFile); 3551 pMP3->pUserData = NULL; /* Make sure the file handle is cleared to NULL to we don't attempt to close it a second time. */ 3552 } 3553 } 3554 #endif 3555 3556 drmp3__free_from_callbacks(pMP3->pData, &pMP3->allocationCallbacks); 3557 } 3558 3559 #if defined(DR_MP3_FLOAT_OUTPUT) 3560 static void drmp3_f32_to_s16(drmp3_int16* dst, const float* src, drmp3_uint64 sampleCount) 3561 { 3562 drmp3_uint64 i; 3563 drmp3_uint64 i4; 3564 drmp3_uint64 sampleCount4; 3565 3566 /* Unrolled. */ 3567 i = 0; 3568 sampleCount4 = sampleCount >> 2; 3569 for (i4 = 0; i4 < sampleCount4; i4 += 1) { 3570 float x0 = src[i+0]; 3571 float x1 = src[i+1]; 3572 float x2 = src[i+2]; 3573 float x3 = src[i+3]; 3574 3575 x0 = ((x0 < -1) ? -1 : ((x0 > 1) ? 1 : x0)); 3576 x1 = ((x1 < -1) ? -1 : ((x1 > 1) ? 1 : x1)); 3577 x2 = ((x2 < -1) ? -1 : ((x2 > 1) ? 1 : x2)); 3578 x3 = ((x3 < -1) ? -1 : ((x3 > 1) ? 1 : x3)); 3579 3580 x0 = x0 * 32767.0f; 3581 x1 = x1 * 32767.0f; 3582 x2 = x2 * 32767.0f; 3583 x3 = x3 * 32767.0f; 3584 3585 dst[i+0] = (drmp3_int16)x0; 3586 dst[i+1] = (drmp3_int16)x1; 3587 dst[i+2] = (drmp3_int16)x2; 3588 dst[i+3] = (drmp3_int16)x3; 3589 3590 i += 4; 3591 } 3592 3593 /* Leftover. */ 3594 for (; i < sampleCount; i += 1) { 3595 float x = src[i]; 3596 x = ((x < -1) ? -1 : ((x > 1) ? 1 : x)); /* clip */ 3597 x = x * 32767.0f; /* -1..1 to -32767..32767 */ 3598 3599 dst[i] = (drmp3_int16)x; 3600 } 3601 } 3602 #endif 3603 3604 #if !defined(DR_MP3_FLOAT_OUTPUT) 3605 static void drmp3_s16_to_f32(float* dst, const drmp3_int16* src, drmp3_uint64 sampleCount) 3606 { 3607 drmp3_uint64 i; 3608 for (i = 0; i < sampleCount; i += 1) { 3609 float x = (float)src[i]; 3610 x = x * 0.000030517578125f; /* -32768..32767 to -1..0.999969482421875 */ 3611 dst[i] = x; 3612 } 3613 } 3614 #endif 3615 3616 3617 static drmp3_uint64 drmp3_read_pcm_frames_raw(drmp3* pMP3, drmp3_uint64 framesToRead, void* pBufferOut) 3618 { 3619 drmp3_uint64 totalFramesRead = 0; 3620 3621 DRMP3_ASSERT(pMP3 != NULL); 3622 DRMP3_ASSERT(pMP3->onRead != NULL); 3623 3624 while (framesToRead > 0) { 3625 drmp3_uint32 framesToConsume = (drmp3_uint32)DRMP3_MIN(pMP3->pcmFramesRemainingInMP3Frame, framesToRead); 3626 if (pBufferOut != NULL) { 3627 #if defined(DR_MP3_FLOAT_OUTPUT) 3628 /* f32 */ 3629 float* pFramesOutF32 = (float*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(float) * totalFramesRead * pMP3->channels); 3630 float* pFramesInF32 = (float*)DRMP3_OFFSET_PTR(&pMP3->pcmFrames[0], sizeof(float) * pMP3->pcmFramesConsumedInMP3Frame * pMP3->mp3FrameChannels); 3631 DRMP3_COPY_MEMORY(pFramesOutF32, pFramesInF32, sizeof(float) * framesToConsume * pMP3->channels); 3632 #else 3633 /* s16 */ 3634 drmp3_int16* pFramesOutS16 = (drmp3_int16*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(drmp3_int16) * totalFramesRead * pMP3->channels); 3635 drmp3_int16* pFramesInS16 = (drmp3_int16*)DRMP3_OFFSET_PTR(&pMP3->pcmFrames[0], sizeof(drmp3_int16) * pMP3->pcmFramesConsumedInMP3Frame * pMP3->mp3FrameChannels); 3636 DRMP3_COPY_MEMORY(pFramesOutS16, pFramesInS16, sizeof(drmp3_int16) * framesToConsume * pMP3->channels); 3637 #endif 3638 } 3639 3640 pMP3->currentPCMFrame += framesToConsume; 3641 pMP3->pcmFramesConsumedInMP3Frame += framesToConsume; 3642 pMP3->pcmFramesRemainingInMP3Frame -= framesToConsume; 3643 totalFramesRead += framesToConsume; 3644 framesToRead -= framesToConsume; 3645 3646 if (framesToRead == 0) { 3647 break; 3648 } 3649 3650 DRMP3_ASSERT(pMP3->pcmFramesRemainingInMP3Frame == 0); 3651 3652 /* 3653 At this point we have exhausted our in-memory buffer so we need to re-fill. Note that the sample rate may have changed 3654 at this point which means we'll also need to update our sample rate conversion pipeline. 3655 */ 3656 if (drmp3_decode_next_frame(pMP3) == 0) { 3657 break; 3658 } 3659 } 3660 3661 return totalFramesRead; 3662 } 3663 3664 3665 DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_f32(drmp3* pMP3, drmp3_uint64 framesToRead, float* pBufferOut) 3666 { 3667 if (pMP3 == NULL || pMP3->onRead == NULL) { 3668 return 0; 3669 } 3670 3671 #if defined(DR_MP3_FLOAT_OUTPUT) 3672 /* Fast path. No conversion required. */ 3673 return drmp3_read_pcm_frames_raw(pMP3, framesToRead, pBufferOut); 3674 #else 3675 /* Slow path. Convert from s16 to f32. */ 3676 { 3677 drmp3_int16 pTempS16[8192]; 3678 drmp3_uint64 totalPCMFramesRead = 0; 3679 3680 while (totalPCMFramesRead < framesToRead) { 3681 drmp3_uint64 framesJustRead; 3682 drmp3_uint64 framesRemaining = framesToRead - totalPCMFramesRead; 3683 drmp3_uint64 framesToReadNow = DRMP3_COUNTOF(pTempS16) / pMP3->channels; 3684 if (framesToReadNow > framesRemaining) { 3685 framesToReadNow = framesRemaining; 3686 } 3687 3688 framesJustRead = drmp3_read_pcm_frames_raw(pMP3, framesToReadNow, pTempS16); 3689 if (framesJustRead == 0) { 3690 break; 3691 } 3692 3693 drmp3_s16_to_f32((float*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(float) * totalPCMFramesRead * pMP3->channels), pTempS16, framesJustRead * pMP3->channels); 3694 totalPCMFramesRead += framesJustRead; 3695 } 3696 3697 return totalPCMFramesRead; 3698 } 3699 #endif 3700 } 3701 3702 DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_s16(drmp3* pMP3, drmp3_uint64 framesToRead, drmp3_int16* pBufferOut) 3703 { 3704 if (pMP3 == NULL || pMP3->onRead == NULL) { 3705 return 0; 3706 } 3707 3708 #if !defined(DR_MP3_FLOAT_OUTPUT) 3709 /* Fast path. No conversion required. */ 3710 return drmp3_read_pcm_frames_raw(pMP3, framesToRead, pBufferOut); 3711 #else 3712 /* Slow path. Convert from f32 to s16. */ 3713 { 3714 float pTempF32[4096]; 3715 drmp3_uint64 totalPCMFramesRead = 0; 3716 3717 while (totalPCMFramesRead < framesToRead) { 3718 drmp3_uint64 framesJustRead; 3719 drmp3_uint64 framesRemaining = framesToRead - totalPCMFramesRead; 3720 drmp3_uint64 framesToReadNow = DRMP3_COUNTOF(pTempF32) / pMP3->channels; 3721 if (framesToReadNow > framesRemaining) { 3722 framesToReadNow = framesRemaining; 3723 } 3724 3725 framesJustRead = drmp3_read_pcm_frames_raw(pMP3, framesToReadNow, pTempF32); 3726 if (framesJustRead == 0) { 3727 break; 3728 } 3729 3730 drmp3_f32_to_s16((drmp3_int16*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(drmp3_int16) * totalPCMFramesRead * pMP3->channels), pTempF32, framesJustRead * pMP3->channels); 3731 totalPCMFramesRead += framesJustRead; 3732 } 3733 3734 return totalPCMFramesRead; 3735 } 3736 #endif 3737 } 3738 3739 static void drmp3_reset(drmp3* pMP3) 3740 { 3741 DRMP3_ASSERT(pMP3 != NULL); 3742 3743 pMP3->pcmFramesConsumedInMP3Frame = 0; 3744 pMP3->pcmFramesRemainingInMP3Frame = 0; 3745 pMP3->currentPCMFrame = 0; 3746 pMP3->dataSize = 0; 3747 pMP3->atEnd = DRMP3_FALSE; 3748 drmp3dec_init(&pMP3->decoder); 3749 } 3750 3751 static drmp3_bool32 drmp3_seek_to_start_of_stream(drmp3* pMP3) 3752 { 3753 DRMP3_ASSERT(pMP3 != NULL); 3754 DRMP3_ASSERT(pMP3->onSeek != NULL); 3755 3756 /* Seek to the start of the stream to begin with. */ 3757 if (!drmp3__on_seek(pMP3, 0, drmp3_seek_origin_start)) { 3758 return DRMP3_FALSE; 3759 } 3760 3761 /* Clear any cached data. */ 3762 drmp3_reset(pMP3); 3763 return DRMP3_TRUE; 3764 } 3765 3766 3767 static drmp3_bool32 drmp3_seek_forward_by_pcm_frames__brute_force(drmp3* pMP3, drmp3_uint64 frameOffset) 3768 { 3769 drmp3_uint64 framesRead; 3770 3771 /* 3772 Just using a dumb read-and-discard for now. What would be nice is to parse only the header of the MP3 frame, and then skip over leading 3773 frames without spending the time doing a full decode. I cannot see an easy way to do this in minimp3, however, so it may involve some 3774 kind of manual processing. 3775 */ 3776 #if defined(DR_MP3_FLOAT_OUTPUT) 3777 framesRead = drmp3_read_pcm_frames_f32(pMP3, frameOffset, NULL); 3778 #else 3779 framesRead = drmp3_read_pcm_frames_s16(pMP3, frameOffset, NULL); 3780 #endif 3781 if (framesRead != frameOffset) { 3782 return DRMP3_FALSE; 3783 } 3784 3785 return DRMP3_TRUE; 3786 } 3787 3788 static drmp3_bool32 drmp3_seek_to_pcm_frame__brute_force(drmp3* pMP3, drmp3_uint64 frameIndex) 3789 { 3790 DRMP3_ASSERT(pMP3 != NULL); 3791 3792 if (frameIndex == pMP3->currentPCMFrame) { 3793 return DRMP3_TRUE; 3794 } 3795 3796 /* 3797 If we're moving foward we just read from where we're at. Otherwise we need to move back to the start of 3798 the stream and read from the beginning. 3799 */ 3800 if (frameIndex < pMP3->currentPCMFrame) { 3801 /* Moving backward. Move to the start of the stream and then move forward. */ 3802 if (!drmp3_seek_to_start_of_stream(pMP3)) { 3803 return DRMP3_FALSE; 3804 } 3805 } 3806 3807 DRMP3_ASSERT(frameIndex >= pMP3->currentPCMFrame); 3808 return drmp3_seek_forward_by_pcm_frames__brute_force(pMP3, (frameIndex - pMP3->currentPCMFrame)); 3809 } 3810 3811 static drmp3_bool32 drmp3_find_closest_seek_point(drmp3* pMP3, drmp3_uint64 frameIndex, drmp3_uint32* pSeekPointIndex) 3812 { 3813 drmp3_uint32 iSeekPoint; 3814 3815 DRMP3_ASSERT(pSeekPointIndex != NULL); 3816 3817 *pSeekPointIndex = 0; 3818 3819 if (frameIndex < pMP3->pSeekPoints[0].pcmFrameIndex) { 3820 return DRMP3_FALSE; 3821 } 3822 3823 /* Linear search for simplicity to begin with while I'm getting this thing working. Once it's all working change this to a binary search. */ 3824 for (iSeekPoint = 0; iSeekPoint < pMP3->seekPointCount; ++iSeekPoint) { 3825 if (pMP3->pSeekPoints[iSeekPoint].pcmFrameIndex > frameIndex) { 3826 break; /* Found it. */ 3827 } 3828 3829 *pSeekPointIndex = iSeekPoint; 3830 } 3831 3832 return DRMP3_TRUE; 3833 } 3834 3835 static drmp3_bool32 drmp3_seek_to_pcm_frame__seek_table(drmp3* pMP3, drmp3_uint64 frameIndex) 3836 { 3837 drmp3_seek_point seekPoint; 3838 drmp3_uint32 priorSeekPointIndex; 3839 drmp3_uint16 iMP3Frame; 3840 drmp3_uint64 leftoverFrames; 3841 3842 DRMP3_ASSERT(pMP3 != NULL); 3843 DRMP3_ASSERT(pMP3->pSeekPoints != NULL); 3844 DRMP3_ASSERT(pMP3->seekPointCount > 0); 3845 3846 /* If there is no prior seekpoint it means the target PCM frame comes before the first seek point. Just assume a seekpoint at the start of the file in this case. */ 3847 if (drmp3_find_closest_seek_point(pMP3, frameIndex, &priorSeekPointIndex)) { 3848 seekPoint = pMP3->pSeekPoints[priorSeekPointIndex]; 3849 } else { 3850 seekPoint.seekPosInBytes = 0; 3851 seekPoint.pcmFrameIndex = 0; 3852 seekPoint.mp3FramesToDiscard = 0; 3853 seekPoint.pcmFramesToDiscard = 0; 3854 } 3855 3856 /* First thing to do is seek to the first byte of the relevant MP3 frame. */ 3857 if (!drmp3__on_seek_64(pMP3, seekPoint.seekPosInBytes, drmp3_seek_origin_start)) { 3858 return DRMP3_FALSE; /* Failed to seek. */ 3859 } 3860 3861 /* Clear any cached data. */ 3862 drmp3_reset(pMP3); 3863 3864 /* Whole MP3 frames need to be discarded first. */ 3865 for (iMP3Frame = 0; iMP3Frame < seekPoint.mp3FramesToDiscard; ++iMP3Frame) { 3866 drmp3_uint32 pcmFramesRead; 3867 drmp3d_sample_t* pPCMFrames; 3868 3869 /* Pass in non-null for the last frame because we want to ensure the sample rate converter is preloaded correctly. */ 3870 pPCMFrames = NULL; 3871 if (iMP3Frame == seekPoint.mp3FramesToDiscard-1) { 3872 pPCMFrames = (drmp3d_sample_t*)pMP3->pcmFrames; 3873 } 3874 3875 /* We first need to decode the next frame. */ 3876 pcmFramesRead = drmp3_decode_next_frame_ex(pMP3, pPCMFrames); 3877 if (pcmFramesRead == 0) { 3878 return DRMP3_FALSE; 3879 } 3880 } 3881 3882 /* We seeked to an MP3 frame in the raw stream so we need to make sure the current PCM frame is set correctly. */ 3883 pMP3->currentPCMFrame = seekPoint.pcmFrameIndex - seekPoint.pcmFramesToDiscard; 3884 3885 /* 3886 Now at this point we can follow the same process as the brute force technique where we just skip over unnecessary MP3 frames and then 3887 read-and-discard at least 2 whole MP3 frames. 3888 */ 3889 leftoverFrames = frameIndex - pMP3->currentPCMFrame; 3890 return drmp3_seek_forward_by_pcm_frames__brute_force(pMP3, leftoverFrames); 3891 } 3892 3893 DRMP3_API drmp3_bool32 drmp3_seek_to_pcm_frame(drmp3* pMP3, drmp3_uint64 frameIndex) 3894 { 3895 if (pMP3 == NULL || pMP3->onSeek == NULL) { 3896 return DRMP3_FALSE; 3897 } 3898 3899 if (frameIndex == 0) { 3900 return drmp3_seek_to_start_of_stream(pMP3); 3901 } 3902 3903 /* Use the seek table if we have one. */ 3904 if (pMP3->pSeekPoints != NULL && pMP3->seekPointCount > 0) { 3905 return drmp3_seek_to_pcm_frame__seek_table(pMP3, frameIndex); 3906 } else { 3907 return drmp3_seek_to_pcm_frame__brute_force(pMP3, frameIndex); 3908 } 3909 } 3910 3911 DRMP3_API drmp3_bool32 drmp3_get_mp3_and_pcm_frame_count(drmp3* pMP3, drmp3_uint64* pMP3FrameCount, drmp3_uint64* pPCMFrameCount) 3912 { 3913 drmp3_uint64 currentPCMFrame; 3914 drmp3_uint64 totalPCMFrameCount; 3915 drmp3_uint64 totalMP3FrameCount; 3916 3917 if (pMP3 == NULL) { 3918 return DRMP3_FALSE; 3919 } 3920 3921 /* 3922 The way this works is we move back to the start of the stream, iterate over each MP3 frame and calculate the frame count based 3923 on our output sample rate, the seek back to the PCM frame we were sitting on before calling this function. 3924 */ 3925 3926 /* The stream must support seeking for this to work. */ 3927 if (pMP3->onSeek == NULL) { 3928 return DRMP3_FALSE; 3929 } 3930 3931 /* We'll need to seek back to where we were, so grab the PCM frame we're currently sitting on so we can restore later. */ 3932 currentPCMFrame = pMP3->currentPCMFrame; 3933 3934 if (!drmp3_seek_to_start_of_stream(pMP3)) { 3935 return DRMP3_FALSE; 3936 } 3937 3938 totalPCMFrameCount = 0; 3939 totalMP3FrameCount = 0; 3940 3941 for (;;) { 3942 drmp3_uint32 pcmFramesInCurrentMP3Frame; 3943 3944 pcmFramesInCurrentMP3Frame = drmp3_decode_next_frame_ex(pMP3, NULL); 3945 if (pcmFramesInCurrentMP3Frame == 0) { 3946 break; 3947 } 3948 3949 totalPCMFrameCount += pcmFramesInCurrentMP3Frame; 3950 totalMP3FrameCount += 1; 3951 } 3952 3953 /* Finally, we need to seek back to where we were. */ 3954 if (!drmp3_seek_to_start_of_stream(pMP3)) { 3955 return DRMP3_FALSE; 3956 } 3957 3958 if (!drmp3_seek_to_pcm_frame(pMP3, currentPCMFrame)) { 3959 return DRMP3_FALSE; 3960 } 3961 3962 if (pMP3FrameCount != NULL) { 3963 *pMP3FrameCount = totalMP3FrameCount; 3964 } 3965 if (pPCMFrameCount != NULL) { 3966 *pPCMFrameCount = totalPCMFrameCount; 3967 } 3968 3969 return DRMP3_TRUE; 3970 } 3971 3972 DRMP3_API drmp3_uint64 drmp3_get_pcm_frame_count(drmp3* pMP3) 3973 { 3974 drmp3_uint64 totalPCMFrameCount; 3975 if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, NULL, &totalPCMFrameCount)) { 3976 return 0; 3977 } 3978 3979 return totalPCMFrameCount; 3980 } 3981 3982 DRMP3_API drmp3_uint64 drmp3_get_mp3_frame_count(drmp3* pMP3) 3983 { 3984 drmp3_uint64 totalMP3FrameCount; 3985 if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, &totalMP3FrameCount, NULL)) { 3986 return 0; 3987 } 3988 3989 return totalMP3FrameCount; 3990 } 3991 3992 static void drmp3__accumulate_running_pcm_frame_count(drmp3* pMP3, drmp3_uint32 pcmFrameCountIn, drmp3_uint64* pRunningPCMFrameCount, float* pRunningPCMFrameCountFractionalPart) 3993 { 3994 float srcRatio; 3995 float pcmFrameCountOutF; 3996 drmp3_uint32 pcmFrameCountOut; 3997 3998 srcRatio = (float)pMP3->mp3FrameSampleRate / (float)pMP3->sampleRate; 3999 DRMP3_ASSERT(srcRatio > 0); 4000 4001 pcmFrameCountOutF = *pRunningPCMFrameCountFractionalPart + (pcmFrameCountIn / srcRatio); 4002 pcmFrameCountOut = (drmp3_uint32)pcmFrameCountOutF; 4003 *pRunningPCMFrameCountFractionalPart = pcmFrameCountOutF - pcmFrameCountOut; 4004 *pRunningPCMFrameCount += pcmFrameCountOut; 4005 } 4006 4007 typedef struct 4008 { 4009 drmp3_uint64 bytePos; 4010 drmp3_uint64 pcmFrameIndex; /* <-- After sample rate conversion. */ 4011 } drmp3__seeking_mp3_frame_info; 4012 4013 DRMP3_API drmp3_bool32 drmp3_calculate_seek_points(drmp3* pMP3, drmp3_uint32* pSeekPointCount, drmp3_seek_point* pSeekPoints) 4014 { 4015 drmp3_uint32 seekPointCount; 4016 drmp3_uint64 currentPCMFrame; 4017 drmp3_uint64 totalMP3FrameCount; 4018 drmp3_uint64 totalPCMFrameCount; 4019 4020 if (pMP3 == NULL || pSeekPointCount == NULL || pSeekPoints == NULL) { 4021 return DRMP3_FALSE; /* Invalid args. */ 4022 } 4023 4024 seekPointCount = *pSeekPointCount; 4025 if (seekPointCount == 0) { 4026 return DRMP3_FALSE; /* The client has requested no seek points. Consider this to be invalid arguments since the client has probably not intended this. */ 4027 } 4028 4029 /* We'll need to seek back to the current sample after calculating the seekpoints so we need to go ahead and grab the current location at the top. */ 4030 currentPCMFrame = pMP3->currentPCMFrame; 4031 4032 /* We never do more than the total number of MP3 frames and we limit it to 32-bits. */ 4033 if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, &totalMP3FrameCount, &totalPCMFrameCount)) { 4034 return DRMP3_FALSE; 4035 } 4036 4037 /* If there's less than DRMP3_SEEK_LEADING_MP3_FRAMES+1 frames we just report 1 seek point which will be the very start of the stream. */ 4038 if (totalMP3FrameCount < DRMP3_SEEK_LEADING_MP3_FRAMES+1) { 4039 seekPointCount = 1; 4040 pSeekPoints[0].seekPosInBytes = 0; 4041 pSeekPoints[0].pcmFrameIndex = 0; 4042 pSeekPoints[0].mp3FramesToDiscard = 0; 4043 pSeekPoints[0].pcmFramesToDiscard = 0; 4044 } else { 4045 drmp3_uint64 pcmFramesBetweenSeekPoints; 4046 drmp3__seeking_mp3_frame_info mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES+1]; 4047 drmp3_uint64 runningPCMFrameCount = 0; 4048 float runningPCMFrameCountFractionalPart = 0; 4049 drmp3_uint64 nextTargetPCMFrame; 4050 drmp3_uint32 iMP3Frame; 4051 drmp3_uint32 iSeekPoint; 4052 4053 if (seekPointCount > totalMP3FrameCount-1) { 4054 seekPointCount = (drmp3_uint32)totalMP3FrameCount-1; 4055 } 4056 4057 pcmFramesBetweenSeekPoints = totalPCMFrameCount / (seekPointCount+1); 4058 4059 /* 4060 Here is where we actually calculate the seek points. We need to start by moving the start of the stream. We then enumerate over each 4061 MP3 frame. 4062 */ 4063 if (!drmp3_seek_to_start_of_stream(pMP3)) { 4064 return DRMP3_FALSE; 4065 } 4066 4067 /* 4068 We need to cache the byte positions of the previous MP3 frames. As a new MP3 frame is iterated, we cycle the byte positions in this 4069 array. The value in the first item in this array is the byte position that will be reported in the next seek point. 4070 */ 4071 4072 /* We need to initialize the array of MP3 byte positions for the leading MP3 frames. */ 4073 for (iMP3Frame = 0; iMP3Frame < DRMP3_SEEK_LEADING_MP3_FRAMES+1; ++iMP3Frame) { 4074 drmp3_uint32 pcmFramesInCurrentMP3FrameIn; 4075 4076 /* The byte position of the next frame will be the stream's cursor position, minus whatever is sitting in the buffer. */ 4077 DRMP3_ASSERT(pMP3->streamCursor >= pMP3->dataSize); 4078 mp3FrameInfo[iMP3Frame].bytePos = pMP3->streamCursor - pMP3->dataSize; 4079 mp3FrameInfo[iMP3Frame].pcmFrameIndex = runningPCMFrameCount; 4080 4081 /* We need to get information about this frame so we can know how many samples it contained. */ 4082 pcmFramesInCurrentMP3FrameIn = drmp3_decode_next_frame_ex(pMP3, NULL); 4083 if (pcmFramesInCurrentMP3FrameIn == 0) { 4084 return DRMP3_FALSE; /* This should never happen. */ 4085 } 4086 4087 drmp3__accumulate_running_pcm_frame_count(pMP3, pcmFramesInCurrentMP3FrameIn, &runningPCMFrameCount, &runningPCMFrameCountFractionalPart); 4088 } 4089 4090 /* 4091 At this point we will have extracted the byte positions of the leading MP3 frames. We can now start iterating over each seek point and 4092 calculate them. 4093 */ 4094 nextTargetPCMFrame = 0; 4095 for (iSeekPoint = 0; iSeekPoint < seekPointCount; ++iSeekPoint) { 4096 nextTargetPCMFrame += pcmFramesBetweenSeekPoints; 4097 4098 for (;;) { 4099 if (nextTargetPCMFrame < runningPCMFrameCount) { 4100 /* The next seek point is in the current MP3 frame. */ 4101 pSeekPoints[iSeekPoint].seekPosInBytes = mp3FrameInfo[0].bytePos; 4102 pSeekPoints[iSeekPoint].pcmFrameIndex = nextTargetPCMFrame; 4103 pSeekPoints[iSeekPoint].mp3FramesToDiscard = DRMP3_SEEK_LEADING_MP3_FRAMES; 4104 pSeekPoints[iSeekPoint].pcmFramesToDiscard = (drmp3_uint16)(nextTargetPCMFrame - mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES-1].pcmFrameIndex); 4105 break; 4106 } else { 4107 size_t i; 4108 drmp3_uint32 pcmFramesInCurrentMP3FrameIn; 4109 4110 /* 4111 The next seek point is not in the current MP3 frame, so continue on to the next one. The first thing to do is cycle the cached 4112 MP3 frame info. 4113 */ 4114 for (i = 0; i < DRMP3_COUNTOF(mp3FrameInfo)-1; ++i) { 4115 mp3FrameInfo[i] = mp3FrameInfo[i+1]; 4116 } 4117 4118 /* Cache previous MP3 frame info. */ 4119 mp3FrameInfo[DRMP3_COUNTOF(mp3FrameInfo)-1].bytePos = pMP3->streamCursor - pMP3->dataSize; 4120 mp3FrameInfo[DRMP3_COUNTOF(mp3FrameInfo)-1].pcmFrameIndex = runningPCMFrameCount; 4121 4122 /* 4123 Go to the next MP3 frame. This shouldn't ever fail, but just in case it does we just set the seek point and break. If it happens, it 4124 should only ever do it for the last seek point. 4125 */ 4126 pcmFramesInCurrentMP3FrameIn = drmp3_decode_next_frame_ex(pMP3, NULL); 4127 if (pcmFramesInCurrentMP3FrameIn == 0) { 4128 pSeekPoints[iSeekPoint].seekPosInBytes = mp3FrameInfo[0].bytePos; 4129 pSeekPoints[iSeekPoint].pcmFrameIndex = nextTargetPCMFrame; 4130 pSeekPoints[iSeekPoint].mp3FramesToDiscard = DRMP3_SEEK_LEADING_MP3_FRAMES; 4131 pSeekPoints[iSeekPoint].pcmFramesToDiscard = (drmp3_uint16)(nextTargetPCMFrame - mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES-1].pcmFrameIndex); 4132 break; 4133 } 4134 4135 drmp3__accumulate_running_pcm_frame_count(pMP3, pcmFramesInCurrentMP3FrameIn, &runningPCMFrameCount, &runningPCMFrameCountFractionalPart); 4136 } 4137 } 4138 } 4139 4140 /* Finally, we need to seek back to where we were. */ 4141 if (!drmp3_seek_to_start_of_stream(pMP3)) { 4142 return DRMP3_FALSE; 4143 } 4144 if (!drmp3_seek_to_pcm_frame(pMP3, currentPCMFrame)) { 4145 return DRMP3_FALSE; 4146 } 4147 } 4148 4149 *pSeekPointCount = seekPointCount; 4150 return DRMP3_TRUE; 4151 } 4152 4153 DRMP3_API drmp3_bool32 drmp3_bind_seek_table(drmp3* pMP3, drmp3_uint32 seekPointCount, drmp3_seek_point* pSeekPoints) 4154 { 4155 if (pMP3 == NULL) { 4156 return DRMP3_FALSE; 4157 } 4158 4159 if (seekPointCount == 0 || pSeekPoints == NULL) { 4160 /* Unbinding. */ 4161 pMP3->seekPointCount = 0; 4162 pMP3->pSeekPoints = NULL; 4163 } else { 4164 /* Binding. */ 4165 pMP3->seekPointCount = seekPointCount; 4166 pMP3->pSeekPoints = pSeekPoints; 4167 } 4168 4169 return DRMP3_TRUE; 4170 } 4171 4172 4173 static float* drmp3__full_read_and_close_f32(drmp3* pMP3, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount) 4174 { 4175 drmp3_uint64 totalFramesRead = 0; 4176 drmp3_uint64 framesCapacity = 0; 4177 float* pFrames = NULL; 4178 float temp[4096]; 4179 4180 DRMP3_ASSERT(pMP3 != NULL); 4181 4182 for (;;) { 4183 drmp3_uint64 framesToReadRightNow = DRMP3_COUNTOF(temp) / pMP3->channels; 4184 drmp3_uint64 framesJustRead = drmp3_read_pcm_frames_f32(pMP3, framesToReadRightNow, temp); 4185 if (framesJustRead == 0) { 4186 break; 4187 } 4188 4189 /* Reallocate the output buffer if there's not enough room. */ 4190 if (framesCapacity < totalFramesRead + framesJustRead) { 4191 drmp3_uint64 oldFramesBufferSize; 4192 drmp3_uint64 newFramesBufferSize; 4193 drmp3_uint64 newFramesCap; 4194 float* pNewFrames; 4195 4196 newFramesCap = framesCapacity * 2; 4197 if (newFramesCap < totalFramesRead + framesJustRead) { 4198 newFramesCap = totalFramesRead + framesJustRead; 4199 } 4200 4201 oldFramesBufferSize = framesCapacity * pMP3->channels * sizeof(float); 4202 newFramesBufferSize = newFramesCap * pMP3->channels * sizeof(float); 4203 if (newFramesBufferSize > (drmp3_uint64)DRMP3_SIZE_MAX) { 4204 break; 4205 } 4206 4207 pNewFrames = (float*)drmp3__realloc_from_callbacks(pFrames, (size_t)newFramesBufferSize, (size_t)oldFramesBufferSize, &pMP3->allocationCallbacks); 4208 if (pNewFrames == NULL) { 4209 drmp3__free_from_callbacks(pFrames, &pMP3->allocationCallbacks); 4210 break; 4211 } 4212 4213 pFrames = pNewFrames; 4214 framesCapacity = newFramesCap; 4215 } 4216 4217 DRMP3_COPY_MEMORY(pFrames + totalFramesRead*pMP3->channels, temp, (size_t)(framesJustRead*pMP3->channels*sizeof(float))); 4218 totalFramesRead += framesJustRead; 4219 4220 /* If the number of frames we asked for is less that what we actually read it means we've reached the end. */ 4221 if (framesJustRead != framesToReadRightNow) { 4222 break; 4223 } 4224 } 4225 4226 if (pConfig != NULL) { 4227 pConfig->channels = pMP3->channels; 4228 pConfig->sampleRate = pMP3->sampleRate; 4229 } 4230 4231 drmp3_uninit(pMP3); 4232 4233 if (pTotalFrameCount) { 4234 *pTotalFrameCount = totalFramesRead; 4235 } 4236 4237 return pFrames; 4238 } 4239 4240 static drmp3_int16* drmp3__full_read_and_close_s16(drmp3* pMP3, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount) 4241 { 4242 drmp3_uint64 totalFramesRead = 0; 4243 drmp3_uint64 framesCapacity = 0; 4244 drmp3_int16* pFrames = NULL; 4245 drmp3_int16 temp[4096]; 4246 4247 DRMP3_ASSERT(pMP3 != NULL); 4248 4249 for (;;) { 4250 drmp3_uint64 framesToReadRightNow = DRMP3_COUNTOF(temp) / pMP3->channels; 4251 drmp3_uint64 framesJustRead = drmp3_read_pcm_frames_s16(pMP3, framesToReadRightNow, temp); 4252 if (framesJustRead == 0) { 4253 break; 4254 } 4255 4256 /* Reallocate the output buffer if there's not enough room. */ 4257 if (framesCapacity < totalFramesRead + framesJustRead) { 4258 drmp3_uint64 newFramesBufferSize; 4259 drmp3_uint64 oldFramesBufferSize; 4260 drmp3_uint64 newFramesCap; 4261 drmp3_int16* pNewFrames; 4262 4263 newFramesCap = framesCapacity * 2; 4264 if (newFramesCap < totalFramesRead + framesJustRead) { 4265 newFramesCap = totalFramesRead + framesJustRead; 4266 } 4267 4268 oldFramesBufferSize = framesCapacity * pMP3->channels * sizeof(drmp3_int16); 4269 newFramesBufferSize = newFramesCap * pMP3->channels * sizeof(drmp3_int16); 4270 if (newFramesBufferSize > (drmp3_uint64)DRMP3_SIZE_MAX) { 4271 break; 4272 } 4273 4274 pNewFrames = (drmp3_int16*)drmp3__realloc_from_callbacks(pFrames, (size_t)newFramesBufferSize, (size_t)oldFramesBufferSize, &pMP3->allocationCallbacks); 4275 if (pNewFrames == NULL) { 4276 drmp3__free_from_callbacks(pFrames, &pMP3->allocationCallbacks); 4277 break; 4278 } 4279 4280 pFrames = pNewFrames; 4281 framesCapacity = newFramesCap; 4282 } 4283 4284 DRMP3_COPY_MEMORY(pFrames + totalFramesRead*pMP3->channels, temp, (size_t)(framesJustRead*pMP3->channels*sizeof(drmp3_int16))); 4285 totalFramesRead += framesJustRead; 4286 4287 /* If the number of frames we asked for is less that what we actually read it means we've reached the end. */ 4288 if (framesJustRead != framesToReadRightNow) { 4289 break; 4290 } 4291 } 4292 4293 if (pConfig != NULL) { 4294 pConfig->channels = pMP3->channels; 4295 pConfig->sampleRate = pMP3->sampleRate; 4296 } 4297 4298 drmp3_uninit(pMP3); 4299 4300 if (pTotalFrameCount) { 4301 *pTotalFrameCount = totalFramesRead; 4302 } 4303 4304 return pFrames; 4305 } 4306 4307 4308 DRMP3_API float* drmp3_open_and_read_pcm_frames_f32(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4309 { 4310 drmp3 mp3; 4311 if (!drmp3_init(&mp3, onRead, onSeek, pUserData, pAllocationCallbacks)) { 4312 return NULL; 4313 } 4314 4315 return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); 4316 } 4317 4318 DRMP3_API drmp3_int16* drmp3_open_and_read_pcm_frames_s16(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4319 { 4320 drmp3 mp3; 4321 if (!drmp3_init(&mp3, onRead, onSeek, pUserData, pAllocationCallbacks)) { 4322 return NULL; 4323 } 4324 4325 return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); 4326 } 4327 4328 4329 DRMP3_API float* drmp3_open_memory_and_read_pcm_frames_f32(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4330 { 4331 drmp3 mp3; 4332 if (!drmp3_init_memory(&mp3, pData, dataSize, pAllocationCallbacks)) { 4333 return NULL; 4334 } 4335 4336 return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); 4337 } 4338 4339 DRMP3_API drmp3_int16* drmp3_open_memory_and_read_pcm_frames_s16(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4340 { 4341 drmp3 mp3; 4342 if (!drmp3_init_memory(&mp3, pData, dataSize, pAllocationCallbacks)) { 4343 return NULL; 4344 } 4345 4346 return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); 4347 } 4348 4349 4350 #ifndef DR_MP3_NO_STDIO 4351 DRMP3_API float* drmp3_open_file_and_read_pcm_frames_f32(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4352 { 4353 drmp3 mp3; 4354 if (!drmp3_init_file(&mp3, filePath, pAllocationCallbacks)) { 4355 return NULL; 4356 } 4357 4358 return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); 4359 } 4360 4361 DRMP3_API drmp3_int16* drmp3_open_file_and_read_pcm_frames_s16(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) 4362 { 4363 drmp3 mp3; 4364 if (!drmp3_init_file(&mp3, filePath, pAllocationCallbacks)) { 4365 return NULL; 4366 } 4367 4368 return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); 4369 } 4370 #endif 4371 4372 DRMP3_API void* drmp3_malloc(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks) 4373 { 4374 if (pAllocationCallbacks != NULL) { 4375 return drmp3__malloc_from_callbacks(sz, pAllocationCallbacks); 4376 } else { 4377 return drmp3__malloc_default(sz, NULL); 4378 } 4379 } 4380 4381 DRMP3_API void drmp3_free(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks) 4382 { 4383 if (pAllocationCallbacks != NULL) { 4384 drmp3__free_from_callbacks(p, pAllocationCallbacks); 4385 } else { 4386 drmp3__free_default(p, NULL); 4387 } 4388 } 4389 4390 #endif /* dr_mp3_c */ 4391 #endif /*DR_MP3_IMPLEMENTATION*/ 4392 4393 /* 4394 DIFFERENCES BETWEEN minimp3 AND dr_mp3 4395 ====================================== 4396 - First, keep in mind that minimp3 (https://github.com/lieff/minimp3) is where all the real work was done. All of the 4397 code relating to the actual decoding remains mostly unmodified, apart from some namespacing changes. 4398 - dr_mp3 adds a pulling style API which allows you to deliver raw data via callbacks. So, rather than pushing data 4399 to the decoder, the decoder _pulls_ data from your callbacks. 4400 - In addition to callbacks, a decoder can be initialized from a block of memory and a file. 4401 - The dr_mp3 pull API reads PCM frames rather than whole MP3 frames. 4402 - dr_mp3 adds convenience APIs for opening and decoding entire files in one go. 4403 - dr_mp3 is fully namespaced, including the implementation section, which is more suitable when compiling projects 4404 as a single translation unit (aka unity builds). At the time of writing this, a unity build is not possible when 4405 using minimp3 in conjunction with stb_vorbis. dr_mp3 addresses this. 4406 */ 4407 4408 /* 4409 RELEASE NOTES - v0.5.0 4410 ======================= 4411 Version 0.5.0 has breaking API changes. 4412 4413 Improved Client-Defined Memory Allocation 4414 ----------------------------------------- 4415 The main change with this release is the addition of a more flexible way of implementing custom memory allocation routines. The 4416 existing system of DRMP3_MALLOC, DRMP3_REALLOC and DRMP3_FREE are still in place and will be used by default when no custom 4417 allocation callbacks are specified. 4418 4419 To use the new system, you pass in a pointer to a drmp3_allocation_callbacks object to drmp3_init() and family, like this: 4420 4421 void* my_malloc(size_t sz, void* pUserData) 4422 { 4423 return malloc(sz); 4424 } 4425 void* my_realloc(void* p, size_t sz, void* pUserData) 4426 { 4427 return realloc(p, sz); 4428 } 4429 void my_free(void* p, void* pUserData) 4430 { 4431 free(p); 4432 } 4433 4434 ... 4435 4436 drmp3_allocation_callbacks allocationCallbacks; 4437 allocationCallbacks.pUserData = &myData; 4438 allocationCallbacks.onMalloc = my_malloc; 4439 allocationCallbacks.onRealloc = my_realloc; 4440 allocationCallbacks.onFree = my_free; 4441 drmp3_init_file(&mp3, "my_file.mp3", NULL, &allocationCallbacks); 4442 4443 The advantage of this new system is that it allows you to specify user data which will be passed in to the allocation routines. 4444 4445 Passing in null for the allocation callbacks object will cause dr_mp3 to use defaults which is the same as DRMP3_MALLOC, 4446 DRMP3_REALLOC and DRMP3_FREE and the equivalent of how it worked in previous versions. 4447 4448 Every API that opens a drmp3 object now takes this extra parameter. These include the following: 4449 4450 drmp3_init() 4451 drmp3_init_file() 4452 drmp3_init_memory() 4453 drmp3_open_and_read_pcm_frames_f32() 4454 drmp3_open_and_read_pcm_frames_s16() 4455 drmp3_open_memory_and_read_pcm_frames_f32() 4456 drmp3_open_memory_and_read_pcm_frames_s16() 4457 drmp3_open_file_and_read_pcm_frames_f32() 4458 drmp3_open_file_and_read_pcm_frames_s16() 4459 4460 Renamed APIs 4461 ------------ 4462 The following APIs have been renamed for consistency with other dr_* libraries and to make it clear that they return PCM frame 4463 counts rather than sample counts. 4464 4465 drmp3_open_and_read_f32() -> drmp3_open_and_read_pcm_frames_f32() 4466 drmp3_open_and_read_s16() -> drmp3_open_and_read_pcm_frames_s16() 4467 drmp3_open_memory_and_read_f32() -> drmp3_open_memory_and_read_pcm_frames_f32() 4468 drmp3_open_memory_and_read_s16() -> drmp3_open_memory_and_read_pcm_frames_s16() 4469 drmp3_open_file_and_read_f32() -> drmp3_open_file_and_read_pcm_frames_f32() 4470 drmp3_open_file_and_read_s16() -> drmp3_open_file_and_read_pcm_frames_s16() 4471 */ 4472 4473 /* 4474 REVISION HISTORY 4475 ================ 4476 v0.6.31 - 2021-08-22 4477 - Fix a bug when loading from memory. 4478 4479 v0.6.30 - 2021-08-16 4480 - Silence some warnings. 4481 - Replace memory operations with DRMP3_* macros. 4482 4483 v0.6.29 - 2021-08-08 4484 - Bring up to date with minimp3. 4485 4486 v0.6.28 - 2021-07-31 4487 - Fix platform detection for ARM64. 4488 - Fix a compilation error with C89. 4489 4490 v0.6.27 - 2021-02-21 4491 - Fix a warning due to referencing _MSC_VER when it is undefined. 4492 4493 v0.6.26 - 2021-01-31 4494 - Bring up to date with minimp3. 4495 4496 v0.6.25 - 2020-12-26 4497 - Remove DRMP3_DEFAULT_CHANNELS and DRMP3_DEFAULT_SAMPLE_RATE which are leftovers from some removed APIs. 4498 4499 v0.6.24 - 2020-12-07 4500 - Fix a typo in version date for 0.6.23. 4501 4502 v0.6.23 - 2020-12-03 4503 - Fix an error where a file can be closed twice when initialization of the decoder fails. 4504 4505 v0.6.22 - 2020-12-02 4506 - Fix an error where it's possible for a file handle to be left open when initialization of the decoder fails. 4507 4508 v0.6.21 - 2020-11-28 4509 - Bring up to date with minimp3. 4510 4511 v0.6.20 - 2020-11-21 4512 - Fix compilation with OpenWatcom. 4513 4514 v0.6.19 - 2020-11-13 4515 - Minor code clean up. 4516 4517 v0.6.18 - 2020-11-01 4518 - Improve compiler support for older versions of GCC. 4519 4520 v0.6.17 - 2020-09-28 4521 - Bring up to date with minimp3. 4522 4523 v0.6.16 - 2020-08-02 4524 - Simplify sized types. 4525 4526 v0.6.15 - 2020-07-25 4527 - Fix a compilation warning. 4528 4529 v0.6.14 - 2020-07-23 4530 - Fix undefined behaviour with memmove(). 4531 4532 v0.6.13 - 2020-07-06 4533 - Fix a bug when converting from s16 to f32 in drmp3_read_pcm_frames_f32(). 4534 4535 v0.6.12 - 2020-06-23 4536 - Add include guard for the implementation section. 4537 4538 v0.6.11 - 2020-05-26 4539 - Fix use of uninitialized variable error. 4540 4541 v0.6.10 - 2020-05-16 4542 - Add compile-time and run-time version querying. 4543 - DRMP3_VERSION_MINOR 4544 - DRMP3_VERSION_MAJOR 4545 - DRMP3_VERSION_REVISION 4546 - DRMP3_VERSION_STRING 4547 - drmp3_version() 4548 - drmp3_version_string() 4549 4550 v0.6.9 - 2020-04-30 4551 - Change the `pcm` parameter of drmp3dec_decode_frame() to a `const drmp3_uint8*` for consistency with internal APIs. 4552 4553 v0.6.8 - 2020-04-26 4554 - Optimizations to decoding when initializing from memory. 4555 4556 v0.6.7 - 2020-04-25 4557 - Fix a compilation error with DR_MP3_NO_STDIO 4558 - Optimization to decoding by reducing some data movement. 4559 4560 v0.6.6 - 2020-04-23 4561 - Fix a minor bug with the running PCM frame counter. 4562 4563 v0.6.5 - 2020-04-19 4564 - Fix compilation error on ARM builds. 4565 4566 v0.6.4 - 2020-04-19 4567 - Bring up to date with changes to minimp3. 4568 4569 v0.6.3 - 2020-04-13 4570 - Fix some pedantic warnings. 4571 4572 v0.6.2 - 2020-04-10 4573 - Fix a crash in drmp3_open_*_and_read_pcm_frames_*() if the output config object is NULL. 4574 4575 v0.6.1 - 2020-04-05 4576 - Fix warnings. 4577 4578 v0.6.0 - 2020-04-04 4579 - API CHANGE: Remove the pConfig parameter from the following APIs: 4580 - drmp3_init() 4581 - drmp3_init_memory() 4582 - drmp3_init_file() 4583 - Add drmp3_init_file_w() for opening a file from a wchar_t encoded path. 4584 4585 v0.5.6 - 2020-02-12 4586 - Bring up to date with minimp3. 4587 4588 v0.5.5 - 2020-01-29 4589 - Fix a memory allocation bug in high level s16 decoding APIs. 4590 4591 v0.5.4 - 2019-12-02 4592 - Fix a possible null pointer dereference when using custom memory allocators for realloc(). 4593 4594 v0.5.3 - 2019-11-14 4595 - Fix typos in documentation. 4596 4597 v0.5.2 - 2019-11-02 4598 - Bring up to date with minimp3. 4599 4600 v0.5.1 - 2019-10-08 4601 - Fix a warning with GCC. 4602 4603 v0.5.0 - 2019-10-07 4604 - API CHANGE: Add support for user defined memory allocation routines. This system allows the program to specify their own memory allocation 4605 routines with a user data pointer for client-specific contextual data. This adds an extra parameter to the end of the following APIs: 4606 - drmp3_init() 4607 - drmp3_init_file() 4608 - drmp3_init_memory() 4609 - drmp3_open_and_read_pcm_frames_f32() 4610 - drmp3_open_and_read_pcm_frames_s16() 4611 - drmp3_open_memory_and_read_pcm_frames_f32() 4612 - drmp3_open_memory_and_read_pcm_frames_s16() 4613 - drmp3_open_file_and_read_pcm_frames_f32() 4614 - drmp3_open_file_and_read_pcm_frames_s16() 4615 - API CHANGE: Renamed the following APIs: 4616 - drmp3_open_and_read_f32() -> drmp3_open_and_read_pcm_frames_f32() 4617 - drmp3_open_and_read_s16() -> drmp3_open_and_read_pcm_frames_s16() 4618 - drmp3_open_memory_and_read_f32() -> drmp3_open_memory_and_read_pcm_frames_f32() 4619 - drmp3_open_memory_and_read_s16() -> drmp3_open_memory_and_read_pcm_frames_s16() 4620 - drmp3_open_file_and_read_f32() -> drmp3_open_file_and_read_pcm_frames_f32() 4621 - drmp3_open_file_and_read_s16() -> drmp3_open_file_and_read_pcm_frames_s16() 4622 4623 v0.4.7 - 2019-07-28 4624 - Fix a compiler error. 4625 4626 v0.4.6 - 2019-06-14 4627 - Fix a compiler error. 4628 4629 v0.4.5 - 2019-06-06 4630 - Bring up to date with minimp3. 4631 4632 v0.4.4 - 2019-05-06 4633 - Fixes to the VC6 build. 4634 4635 v0.4.3 - 2019-05-05 4636 - Use the channel count and/or sample rate of the first MP3 frame instead of DRMP3_DEFAULT_CHANNELS and 4637 DRMP3_DEFAULT_SAMPLE_RATE when they are set to 0. To use the old behaviour, just set the relevant property to 4638 DRMP3_DEFAULT_CHANNELS or DRMP3_DEFAULT_SAMPLE_RATE. 4639 - Add s16 reading APIs 4640 - drmp3_read_pcm_frames_s16 4641 - drmp3_open_memory_and_read_pcm_frames_s16 4642 - drmp3_open_and_read_pcm_frames_s16 4643 - drmp3_open_file_and_read_pcm_frames_s16 4644 - Add drmp3_get_mp3_and_pcm_frame_count() to the public header section. 4645 - Add support for C89. 4646 - Change license to choice of public domain or MIT-0. 4647 4648 v0.4.2 - 2019-02-21 4649 - Fix a warning. 4650 4651 v0.4.1 - 2018-12-30 4652 - Fix a warning. 4653 4654 v0.4.0 - 2018-12-16 4655 - API CHANGE: Rename some APIs: 4656 - drmp3_read_f32 -> to drmp3_read_pcm_frames_f32 4657 - drmp3_seek_to_frame -> drmp3_seek_to_pcm_frame 4658 - drmp3_open_and_decode_f32 -> drmp3_open_and_read_pcm_frames_f32 4659 - drmp3_open_and_decode_memory_f32 -> drmp3_open_memory_and_read_pcm_frames_f32 4660 - drmp3_open_and_decode_file_f32 -> drmp3_open_file_and_read_pcm_frames_f32 4661 - Add drmp3_get_pcm_frame_count(). 4662 - Add drmp3_get_mp3_frame_count(). 4663 - Improve seeking performance. 4664 4665 v0.3.2 - 2018-09-11 4666 - Fix a couple of memory leaks. 4667 - Bring up to date with minimp3. 4668 4669 v0.3.1 - 2018-08-25 4670 - Fix C++ build. 4671 4672 v0.3.0 - 2018-08-25 4673 - Bring up to date with minimp3. This has a minor API change: the "pcm" parameter of drmp3dec_decode_frame() has 4674 been changed from short* to void* because it can now output both s16 and f32 samples, depending on whether or 4675 not the DR_MP3_FLOAT_OUTPUT option is set. 4676 4677 v0.2.11 - 2018-08-08 4678 - Fix a bug where the last part of a file is not read. 4679 4680 v0.2.10 - 2018-08-07 4681 - Improve 64-bit detection. 4682 4683 v0.2.9 - 2018-08-05 4684 - Fix C++ build on older versions of GCC. 4685 - Bring up to date with minimp3. 4686 4687 v0.2.8 - 2018-08-02 4688 - Fix compilation errors with older versions of GCC. 4689 4690 v0.2.7 - 2018-07-13 4691 - Bring up to date with minimp3. 4692 4693 v0.2.6 - 2018-07-12 4694 - Bring up to date with minimp3. 4695 4696 v0.2.5 - 2018-06-22 4697 - Bring up to date with minimp3. 4698 4699 v0.2.4 - 2018-05-12 4700 - Bring up to date with minimp3. 4701 4702 v0.2.3 - 2018-04-29 4703 - Fix TCC build. 4704 4705 v0.2.2 - 2018-04-28 4706 - Fix bug when opening a decoder from memory. 4707 4708 v0.2.1 - 2018-04-27 4709 - Efficiency improvements when the decoder reaches the end of the stream. 4710 4711 v0.2 - 2018-04-21 4712 - Bring up to date with minimp3. 4713 - Start using major.minor.revision versioning. 4714 4715 v0.1d - 2018-03-30 4716 - Bring up to date with minimp3. 4717 4718 v0.1c - 2018-03-11 4719 - Fix C++ build error. 4720 4721 v0.1b - 2018-03-07 4722 - Bring up to date with minimp3. 4723 4724 v0.1a - 2018-02-28 4725 - Fix compilation error on GCC/Clang. 4726 - Fix some warnings. 4727 4728 v0.1 - 2018-02-xx 4729 - Initial versioned release. 4730 */ 4731 4732 /* 4733 This software is available as a choice of the following licenses. Choose 4734 whichever you prefer. 4735 4736 =============================================================================== 4737 ALTERNATIVE 1 - Public Domain (www.unlicense.org) 4738 =============================================================================== 4739 This is free and unencumbered software released into the public domain. 4740 4741 Anyone is free to copy, modify, publish, use, compile, sell, or distribute this 4742 software, either in source code form or as a compiled binary, for any purpose, 4743 commercial or non-commercial, and by any means. 4744 4745 In jurisdictions that recognize copyright laws, the author or authors of this 4746 software dedicate any and all copyright interest in the software to the public 4747 domain. We make this dedication for the benefit of the public at large and to 4748 the detriment of our heirs and successors. We intend this dedication to be an 4749 overt act of relinquishment in perpetuity of all present and future rights to 4750 this software under copyright law. 4751 4752 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 4753 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 4754 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 4755 AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN 4756 ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 4757 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 4758 4759 For more information, please refer to <http://unlicense.org/> 4760 4761 =============================================================================== 4762 ALTERNATIVE 2 - MIT No Attribution 4763 =============================================================================== 4764 Copyright 2020 David Reid 4765 4766 Permission is hereby granted, free of charge, to any person obtaining a copy of 4767 this software and associated documentation files (the "Software"), to deal in 4768 the Software without restriction, including without limitation the rights to 4769 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies 4770 of the Software, and to permit persons to whom the Software is furnished to do 4771 so. 4772 4773 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 4774 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 4775 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 4776 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 4777 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 4778 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 4779 SOFTWARE. 4780 */ 4781 4782 /* 4783 https://github.com/lieff/minimp3 4784 To the extent possible under law, the author(s) have dedicated all copyright and related and neighboring rights to this software to the public domain worldwide. 4785 This software is distributed without any warranty. 4786 See <http://creativecommons.org/publicdomain/zero/1.0/>. 4787 */