📄 g721.c
字号:
// // The initial time position is zero. // pG721->ulTimePos = 0; // // Start play from the fifth byte of the buffer. // pG721->usOffset = 4; // // Compute the length of the file in milliseconds. // pG721->ulTimeLength = (pG721->ulLength - 4) / 4; } // // There is no input/output buffer. // pG721->pBuffer = 0; // // Success. // return(1); } // // Get the capture buffer for the encoder. // case IOCTL_CODEC_GETCAPTUREBUFFER: { tG721 *pG721; short **ppsBuffer; long *plLength; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // The second parameter is a pointer to the capture buffer. // ppsBuffer = (short **)ulParam2; // // The third parameter is a pointer to the length of the capture // buffer. // plLength = (long *)ulParam3; // // Return the capture buffer. // *ppsBuffer = pG721->psRawData; *plLength = 4096; // // Success. // return(1); } // // Set the output buffer for the decoder. // case IOCTL_CODEC_SETBUFFER: { tG721 *pG721; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // The second parameter is a pointer to the input/output buffer. // pG721->pBuffer = (BufferState *)ulParam2; // // Provide the input/output buffer with our data buffer. // BufferSetBuffer(pG721->pBuffer, pG721->psSRCData, pG721->psSRCData, 512); // // Success. // return(1); } // // Determine if the next "frame" of data can be decoded. // case IOCTL_CODEC_CAN_DECODE: { tG721 *pG721; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // See if there is space available for decoding the next frame. // if(BufferSpaceAvailable(pG721->pBuffer) < 256) { // // There is not enough space available, so we can not decode // the next frame. // return(0); } // // We can decode the next frame. // return(1); } // // Decode a "frame" of data (which we arbitrarily set as 256 samples). // case IOCTL_CODEC_DECODE: { tG721 *pG721; short *psLeft, *psRight; long lLength, lLoop; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // See if we've reached the end of the file. // if((pG721->usValid == pG721->usOffset) && (pG721->ulFilePos == pG721->ulLength)) { return(0); } // // Wait until there is enough space in the output buffer. // while(BufferSpaceAvailable(pG721->pBuffer) < 256) { // // Busy wait until space is available. // } // // Get the write pointer for the output buffer. // BufferGetWritePointer(pG721->pBuffer, &psLeft, &psRight, &lLength); // // Determine how many G.721 samples to uncompress, up to a maximum // of 256. // if((pG721->usValid - pG721->usOffset) < 128) { lLength = (pG721->usValid - pG721->usOffset) * 2; } else { lLength = 256; } // // Uncompress the G.721 samples. // for(lLoop = 0; lLoop < lLength; lLoop += 2, pG721->usOffset++) { // // Uncompress the lower nibble of this byte. // *psLeft++ = g721_decoder(pG721->pcEncodedData[pG721->usOffset] & 15, AUDIO_ENCODING_LINEAR, &(pG721->sG721)); // // Uncompress the upper nibble of this byte. // *psLeft++ = g721_decoder(pG721->pcEncodedData[pG721->usOffset] >> 4, AUDIO_ENCODING_LINEAR, &(pG721->sG721)); } // // Zero-pad the remainder of the 256 sample buffer. // for(; lLoop < 256; lLoop += 2) { *psLeft++ = 0; *psLeft++ = 0; } // // Update the output buffer write pointer. // BufferUpdateWritePointer(pG721->pBuffer, 256); // // Increment the time. // pG721->ulTimePos += lLength; // // See if we need to read more data from the file. // if(((pG721->usValid - pG721->usOffset) < 128) && (pG721->ulFilePos != pG721->ulLength)) { // // Copy the tail of the buffer to the beginning. // memcpy(pG721->pcEncodedData, pG721->pcEncodedData + pG721->usOffset, pG721->usValid - pG721->usOffset); // // Read the next 512 bytes from the file. // FSRead(pG721->pFile, pG721->pcEncodedData + pG721->usValid - pG721->usOffset, 512); // // Update the buffer pointers. // if((pG721->ulLength - pG721->ulFilePos) < 512) { pG721->usValid += pG721->ulLength - pG721->ulFilePos - pG721->usOffset; } else { pG721->usValid += 512 - pG721->usOffset; } pG721->usOffset = 0; // // Update the position within the file. // pG721->ulFilePos += 512; if(pG721->ulFilePos > pG721->ulLength) { pG721->ulFilePos = pG721->ulLength; } } // // Success. // return(1); } // // Determine if the next frame of data can be encoded. // case IOCTL_CODEC_CAN_ENCODE: { tG721 *pG721; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // See if there is enough data in the input buffer. // if(BufferDataAvailable(pG721->pBuffer) < 256) { // // There is not enough data available, so we can not encode the // next frame. // return(0); } // // We can encode the next frame. // return(1); } // // Encode a frame of data. // case IOCTL_CODEC_ENCODE: { tG721 *pG721; short *psLeft, *psRight; long lLength, lLoop; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // Wait until there is enough data in the input buffer. // while(BufferDataAvailable(pG721->pBuffer) < 256) { // // Busy wait until data is available. // } // // Get the read pointer for the input buffer. // BufferGetReadPointer(pG721->pBuffer, &psLeft, &psRight, &lLength); // // Compress the samples into G.721 samples. // for(lLoop = 0; lLoop < 256; lLoop += 2) { // // Compress the next two samples and pack them into a single // byte. // pG721->pcEncodedData[pG721->usValid] = g721_encoder(*psLeft++, AUDIO_ENCODING_LINEAR, &(pG721->sG721)); pG721->pcEncodedData[pG721->usValid++] |= g721_encoder(*psLeft++, AUDIO_ENCODING_LINEAR, &(pG721->sG721)) << 4; } // // Update the read pointer for the input buffer. // BufferUpdateReadPointer(pG721->pBuffer, 256); // // If there is enough data in the encoded data buffer, then write // it to the file. // if(pG721->usValid >= 512) { // // Write 512 bytes of data to the file. // if(FSWrite(pG721->pFile, pG721->pcEncodedData, 512) == 0) { return(0); } // // There are now 512 less samples in the encoded data buffer. // pG721->usValid -= 512; // // Copy the valid data from the end of the buffer to the // beginning. // memcpy(pG721->pcEncodedData, pG721->pcEncodedData + 512, pG721->usValid); } // // Increment the time. // pG721->ulTimePos += 256; // // Success. // return(1); } // // Seek to the specified time position. // case IOCTL_CODEC_SEEK: { tG721 *pG721; // // The first parameter is a pointer to the G.721 persistent state. // pG721 = (tG721 *)ulParam1; // // Make sure that the specified time is valid. // if(ulParam2 > pG721->ulTimeLength) { ulParam2 = pG721->ulTimeLength; } // // Compute the position in the file of the seek point (adjusted to // a 512 byte boundary). // pG721->ulFilePos = ((ulParam2 * 4) + 256) & ~511; // // Compute the time for the computed file position. // pG721->ulTimePos = (pG721->ulFilePos - 4) * 2; // // Reposition the file pointer to the computed offset. // FSSeek(pG721->pFile, pG721->ulFilePos); // // There is no valid data in the input buffer. // pG721->usOffset = 0; pG721->usValid = 0; // // Initialize the G.721 decoder. // g72x_init_state(&(pG721->sG721)); // // Success. // return(1); } // // Cleanup after the codec. // case IOCTL_CODEC_CLOSE: { // // There's nothing to do, so return success. // return(1); } // // We should never get here, but just in case... // default: { // // Return a failure. // return(0); } }}#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -