Changeset 1366

Show
Ignore:
Timestamp:
04/24/08 18:27:37 (7 months ago)
Author:
stephen_booth
Message:

Correct handling of 24-bit audio streams
Fixes #6

Location:
trunk
Files:
11 modified

Legend:

Unmodified
Added
Removed
  • trunk/Decoders/FLACDecoder.m

    r1339 r1366  
    8585                case 24:                                 
    8686                         
    87                         // Interleave the audio 
     87                        // Interleave the audio, converting to big endian byte order 
    8888                        alias8 = [[source pcmBuffer] exposeBufferForWriting]; 
    8989                        for(sample = 0; sample < frame->header.blocksize; ++sample) { 
    9090                                for(channel = 0; channel < frame->header.channels; ++channel) { 
    91                                         audioSample     = buffer[channel][sample]; 
    92 #if __BIG_ENDIAN__ 
    93                                         *alias8++       = (int8_t)(audioSample >> 16); 
    94                                         *alias8++       = (int8_t)(audioSample >> 8); 
    95                                         *alias8++       = (int8_t)audioSample; 
    96 #else 
    97                                         *alias8++       = (int8_t)audioSample; 
    98                                         *alias8++       = (int8_t)(audioSample >> 8); 
    99                                         *alias8++       = (int8_t)(audioSample >> 16); 
    100 #endif 
     91                                        audioSample     = OSSwapHostToBigInt32(buffer[channel][sample]); 
     92                                        // Skip the lowest byte 
     93                                        *alias8++       = (int8_t)((audioSample & 0x0000ff00) >> 8); 
     94                                        *alias8++       = (int8_t)((audioSample & 0x00ff0000) >> 16); 
     95                                        *alias8++       = (int8_t)((audioSample & 0xff000000) >> 24); 
    10196                                } 
    10297                        } 
    103                                  
     98                         
    10499                        [[source pcmBuffer] wroteBytes:spaceRequired]; 
    105100                         
  • trunk/Decoders/LibsndfileDecoder.m

    r1339 r1366  
    166166                                        alias8 = [buffer exposeBufferForWriting]; 
    167167                                        for(sample = 0; sample < frameCount * [self pcmFormat].mChannelsPerFrame; ++sample) { 
    168                                                 audioSample     = (doubleBuffer[sample] * (1 << 23)); 
    169 #if __BIG_ENDIAN__ 
    170                                                 *alias8++       = (int8_t)(audioSample >> 16); 
    171                                                 *alias8++       = (int8_t)(audioSample >> 8); 
    172                                                 *alias8++       = (int8_t)audioSample; 
    173 #else 
    174                                                 *alias8++       = (int8_t)audioSample; 
    175                                                 *alias8++       = (int8_t)(audioSample >> 8); 
    176                                                 *alias8++       = (int8_t)(audioSample >> 16); 
    177 #endif 
     168                                                audioSample     = OSSwapHostToBigInt32(doubleBuffer[sample] * (1 << 23)); 
     169                                                // Skip the lowest byte 
     170                                                *alias8++       = (int8_t)((audioSample & 0x0000ff00) >> 8); 
     171                                                *alias8++       = (int8_t)((audioSample & 0x00ff0000) >> 16); 
     172                                                *alias8++       = (int8_t)((audioSample & 0xff000000) >> 24); 
    178173                                        } 
    179174                                                 
  • trunk/Decoders/OggFLACDecoder.m

    r1339 r1366  
    8585                case 24:                                 
    8686                         
    87                         // Interleave the audio (no need for byte swapping) 
     87                        // Interleave the audio, converting to big endian byte order 
    8888                        alias8 = [[source pcmBuffer] exposeBufferForWriting]; 
    8989                        for(sample = 0; sample < frame->header.blocksize; ++sample) { 
    9090                                for(channel = 0; channel < frame->header.channels; ++channel) { 
    91                                         audioSample     = buffer[channel][sample]; 
    92 #if __BIG_ENDIAN__ 
    93                                         *alias8++       = (int8_t)(audioSample >> 16); 
    94                                         *alias8++       = (int8_t)(audioSample >> 8); 
    95                                         *alias8++       = (int8_t)audioSample; 
    96 #else 
    97                                         *alias8++       = (int8_t)audioSample; 
    98                                         *alias8++       = (int8_t)(audioSample >> 8); 
    99                                         *alias8++       = (int8_t)(audioSample >> 16); 
    100 #endif 
    101                                 } 
    102                         } 
    103                                  
    104                                 [[source pcmBuffer] wroteBytes:spaceRequired]; 
     91                                        audioSample     = OSSwapHostToBigInt32(buffer[channel][sample]); 
     92                                        // Skip the lowest byte 
     93                                        *alias8++       = (int8_t)((audioSample & 0x0000ff00) >> 8); 
     94                                        *alias8++       = (int8_t)((audioSample & 0x00ff0000) >> 16); 
     95                                        *alias8++       = (int8_t)((audioSample & 0xff000000) >> 24); 
     96                                } 
     97                        } 
     98                         
     99                        [[source pcmBuffer] wroteBytes:spaceRequired]; 
    105100                         
    106101                        break; 
  • trunk/Decoders/WavPackDecoder.m

    r1359 r1366  
    122122                                alias8 = [buffer exposeBufferForWriting]; 
    123123                                for(sample = 0; sample < samplesRead * [self pcmFormat].mChannelsPerFrame; ++sample) { 
    124                                         audioSample     = inputBuffer[sample]; 
    125 #if __BIG_ENDIAN__ 
    126                                         *alias8++       = (int8_t)(audioSample >> 16); 
    127                                         *alias8++       = (int8_t)(audioSample >> 8); 
    128                                         *alias8++       = (int8_t)audioSample; 
    129 #else 
    130                                         *alias8++       = (int8_t)audioSample; 
    131                                         *alias8++       = (int8_t)(audioSample >> 8); 
    132                                         *alias8++       = (int8_t)(audioSample >> 16); 
    133 #endif 
     124                                        audioSample     = OSSwapHostToBigInt32(inputBuffer[sample]); 
     125                                        // Skip the lowest byte 
     126                                        *alias8++       = (int8_t)((audioSample & 0x0000ff00) >> 8); 
     127                                        *alias8++       = (int8_t)((audioSample & 0x00ff0000) >> 16); 
     128                                        *alias8++       = (int8_t)((audioSample & 0xff000000) >> 24); 
    134129                                } 
    135130                                         
  • trunk/Encoders/FLACEncoder.m

    r1292 r1366  
    384384                                for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    385385                                        for(channel = 0; channel < chunk->mBuffers[0].mNumberChannels; ++channel, ++sample) { 
    386                                                 // We need the sign bit off of the first byte 
    387                                                 constructedSample       = (int32_t)buffer8[sample]; 
    388                                                 constructedSample       <<= 8; 
    389                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
    390                                                 constructedSample       <<= 8; 
    391                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
    392  
    393                                                 buffer[channel][wideSample] = (int32_t)OSSwapBigToHostInt32(constructedSample); 
     386                                                // Read three bytes and reconstruct them as a 32-bit BE integer 
     387                                                constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     388                                                constructedSample = OSSwapBigToHostInt32(constructedSample); 
     389 
     390                                                buffer[channel][wideSample] = constructedSample; 
    394391                                        } 
    395392                                } 
  • trunk/Encoders/LibsndfileEncoder.m

    r1292 r1366  
    176176                                        for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    177177                                                for(channel = 0; channel < bufferList.mBuffers[0].mNumberChannels; ++channel, ++sample) { 
    178                                                         // We need the sign bit off of the first byte 
    179                                                         constructedSample       = (int32_t)buffer8[sample]; 
    180                                                         constructedSample       <<= 8; 
    181                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
    182                                                         constructedSample       <<= 8; 
    183                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
     178                                                        // Read three bytes and reconstruct them as a 32-bit BE integer 
     179                                                        constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     180                                                        constructedSample = OSSwapBigToHostInt32(constructedSample); 
    184181                                                         
    185                                                         buf[(bufferList.mBuffers[0].mNumberChannels * wideSample) + channel] = (int32_t)OSSwapBigToHostInt32(constructedSample); 
    186                                                         buf[(bufferList.mBuffers[0].mNumberChannels * wideSample) + channel] <<= 8; 
     182                                                        buf[(bufferList.mBuffers[0].mNumberChannels * wideSample) + channel] = ((constructedSample << 8) | constructedSample); 
    187183                                                } 
    188184                                        } 
  • trunk/Encoders/MP3Encoder.m

    r1344 r1366  
    342342        int32_t                 *buffer32                               = NULL; 
    343343         
    344         int8_t                  byteOne, byteTwo, byteThree; 
    345344        int32_t                 constructedSample; 
    346345         
     
    420419                                for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    421420                                        for(channel = 0; channel < chunk->mBuffers[0].mNumberChannels; ++channel, ++sample) { 
    422                                                 // Reconstruct the original sample 
    423                                                 byteOne                         = buffer8[sample]; 
    424                                                 byteTwo                         = buffer8[++sample]; 
    425                                                 byteThree                       = buffer8[++sample]; 
    426 #if __BIG_ENDIAN 
    427                                                 constructedSample       = ((byteOne << 16) & 0xFF0000) | ((byteTwo << 8) & 0xFF00) | (byteThree & 0xFF); 
    428 #else 
    429                                                 constructedSample       = ((byteThree << 16) & 0xFF0000) | ((byteTwo << 8) & 0xFF00) | (byteOne & 0xFF); 
    430 #endif 
     421                                                // Read three bytes and reconstruct them as a 32-bit BE integer 
     422                                                constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     423                                                constructedSample = OSSwapBigToHostInt32(constructedSample); 
    431424                                                 
    432425                                                // Convert to 32-bit sample scaling 
    433                                                 channelBuffers32[channel][wideSample] = (long)((constructedSample << 8) | constructedSample); 
     426                                                channelBuffers32[channel][wideSample] = (long)((constructedSample << 8) | (constructedSample & 0x000000ff)); 
    434427                                        } 
    435428                                } 
  • trunk/Encoders/OggFLACEncoder.m

    r1292 r1366  
    344344                                for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    345345                                        for(channel = 0; channel < chunk->mBuffers[0].mNumberChannels; ++channel, ++sample) {                                            
    346                                                 // We need the sign bit off of the first byte 
    347                                                 constructedSample       = (int32_t)buffer8[sample]; 
    348                                                 constructedSample       <<= 8; 
    349                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
    350                                                 constructedSample       <<= 8; 
    351                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
     346                                                // Read three bytes and reconstruct them as a 32-bit BE integer 
     347                                                constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     348                                                constructedSample = OSSwapBigToHostInt32(constructedSample); 
    352349                                                 
    353                                                 buffer[channel][wideSample] = (int32_t)OSSwapBigToHostInt32(constructedSample); 
     350                                                buffer[channel][wideSample] = constructedSample; 
    354351                                        } 
    355352                                } 
  • trunk/Encoders/OggSpeexEncoder.m

    r1292 r1366  
    423423                                        buffer8 = bufferList.mBuffers[0].mData; 
    424424                                        for(wideSample = sample = 0; wideSample < frameCount && sample < bufferList.mBuffers[0].mDataByteSize; ++wideSample, ++sample) { 
    425                                                 // We need the sign bit off of the first byte 
    426                                                 constructedSample       = (int32_t)buffer8[sample]; 
    427                                                 constructedSample       <<= 8; 
    428                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
    429                                                 constructedSample       <<= 8; 
    430                                                 constructedSample       |= (uint8_t)buffer8[++sample]; 
     425                                                // Read three bytes and reconstruct them as a 32-bit BE integer 
     426                                                constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     427                                                constructedSample = OSSwapBigToHostInt32(constructedSample); 
    431428                                                 
    432                                                 floatBuffer[wideSample] = ((int32_t)OSSwapBigToHostInt32(constructedSample) / 8388608.); 
     429                                                floatBuffer[wideSample] = (constructedSample / 8388608.); 
    433430                                        } 
    434431                                        break; 
  • trunk/Encoders/OggVorbisEncoder.m

    r1292 r1366  
    234234                                        for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    235235                                                for(channel = 0; channel < bufferList.mBuffers[0].mNumberChannels; ++channel, ++sample) { 
    236                                                         // We need the sign bit off of the first byte 
    237                                                         constructedSample       = (int32_t)buffer8[sample]; 
    238                                                         constructedSample       <<= 8; 
    239                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
    240                                                         constructedSample       <<= 8; 
    241                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
     236                                                        // Read three bytes and reconstruct them as a 32-bit BE integer 
     237                                                        constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     238                                                        constructedSample = OSSwapBigToHostInt32(constructedSample); 
    242239                                                         
    243                                                         buffer[channel][wideSample] = ((int32_t)OSSwapBigToHostInt32(constructedSample) / 8388608.); 
     240                                                        buffer[channel][wideSample] = (constructedSample / 8388608.); 
    244241                                                } 
    245242                                        } 
  • trunk/Encoders/WavPackEncoder.m

    r1292 r1366  
    221221                                        for(wideSample = sample = 0; wideSample < frameCount; ++wideSample) { 
    222222                                                for(channel = 0; channel < bufferList.mBuffers[0].mNumberChannels; ++channel, ++sample) { 
    223                                                         // We need the sign bit off of the first byte 
    224                                                         constructedSample       = (int32_t)buffer8[sample]; 
    225                                                         constructedSample       <<= 8; 
    226                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
    227                                                         constructedSample       <<= 8; 
    228                                                         constructedSample       |= (uint8_t)buffer8[++sample]; 
     223                                                        // Read three bytes and reconstruct them as a 32-bit BE integer 
     224                                                        constructedSample = (((int32_t)buffer8[sample] << 8) & 0x0000ff00) | (((int32_t)buffer8[++sample] << 16) & 0x00ff0000) | (((int32_t)buffer8[++sample] << 24) & 0xff000000); 
     225                                                        constructedSample = OSSwapBigToHostInt32(constructedSample); 
    229226                                                         
    230                                                         wpBuf[(bufferList.mBuffers[0].mNumberChannels * wideSample) + channel] = (int32_t)OSSwapBigToHostInt32(constructedSample); 
     227                                                        wpBuf[(bufferList.mBuffers[0].mNumberChannels * wideSample) + channel] = constructedSample; 
    231228                                                } 
    232229                                        }