Changeset 4278 for pjproject/trunk/pjmedia/src/pjmedia-codec/silk.c
- Timestamp:
- Oct 5, 2012 10:04:54 AM (12 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
pjproject/trunk/pjmedia/src/pjmedia-codec/silk.c
r4272 r4278 21 21 #include <pjmedia-codec/silk.h> 22 22 #include <pjmedia/codec.h> 23 #include <pjmedia/delaybuf.h> 23 24 #include <pjmedia/endpoint.h> 24 25 #include <pjmedia/errno.h> … … 34 35 35 36 #define THIS_FILE "silk.c" 37 38 #ifndef PJMEDIA_SILK_DELAY_BUF_OPTIONS 39 #define PJMEDIA_SILK_DELAY_BUF_OPTIONS PJMEDIA_DELAY_BUF_SIMPLE_FIFO 40 #endif 36 41 37 42 #define FRAME_LENGTH_MS 20 … … 149 154 pj_pool_t *pool; /**< Pool for each instance. */ 150 155 unsigned samples_per_frame; 156 pj_uint8_t pcm_bytes_per_sample; 151 157 152 158 pj_bool_t enc_ready; … … 157 163 SKP_SILK_SDK_DecControlStruct dec_ctl; 158 164 void *dec_st; 165 166 /* Buffer to hold decoded frames. */ 167 void *dec_buf[SILK_MAX_FRAMES_PER_PACKET-1]; 168 SKP_int16 dec_buf_size[SILK_MAX_FRAMES_PER_PACKET-1]; 169 pj_size_t dec_buf_sz; 170 unsigned dec_buf_cnt; 171 pj_uint32_t pkt_info; /**< Packet info for buffered frames. */ 159 172 } silk_private; 160 173 … … 219 232 sp->pt = PJMEDIA_RTP_PT_SILK_NB; 220 233 sp->clock_rate = 8000; 221 sp->max_bitrate = 2 0000;234 sp->max_bitrate = 22000; 222 235 sp->bitrate = CALC_BITRATE(sp->max_bitrate); 223 236 sp->ptime = FRAME_LENGTH_MS; … … 228 241 sp->pt = PJMEDIA_RTP_PT_SILK_MB; 229 242 sp->clock_rate = 12000; 230 sp->max_bitrate = 2 5000;243 sp->max_bitrate = 28000; 231 244 sp->bitrate = CALC_BITRATE(sp->max_bitrate); 232 245 sp->ptime = FRAME_LENGTH_MS; … … 237 250 sp->pt = PJMEDIA_RTP_PT_SILK_WB; 238 251 sp->clock_rate = 16000; 239 sp->max_bitrate = 3 0000;252 sp->max_bitrate = 36000; 240 253 sp->bitrate = CALC_BITRATE(sp->max_bitrate); 241 254 sp->ptime = FRAME_LENGTH_MS; … … 246 259 sp->pt = PJMEDIA_RTP_PT_SILK_SWB; 247 260 sp->clock_rate = 24000; 248 sp->max_bitrate = 4 0000;261 sp->max_bitrate = 46000; 249 262 sp->bitrate = CALC_BITRATE(sp->max_bitrate); 250 263 sp->ptime = FRAME_LENGTH_MS; … … 597 610 silk->samples_per_frame = attr->setting.frm_per_pkt * FRAME_LENGTH_MS * 598 611 attr->info.clock_rate / 1000; 612 silk->pcm_bytes_per_sample = attr->info.pcm_bits_per_sample / 8; 599 613 600 614 silk->enc_ctl.API_sampleRate = attr->info.clock_rate; … … 626 640 silk->dec_ctl.framesPerPacket = 1; /* for proper PLC at start */ 627 641 silk->dec_ready = PJ_TRUE; 628 629 /* Increase max_bps (as the bitrate values in the table seems to be 630 * rounded down, and without increasing this, frame size of the jitter 631 * buffer has been found lower than the actual frame size, which in turn 632 * it causes noise as the payloads get trimmed). 642 silk->dec_buf_sz = attr->info.clock_rate * attr->info.channel_cnt * 643 attr->info.frm_ptime / 1000 * 644 silk->pcm_bytes_per_sample; 645 646 /* Inform the stream to prepare a larger buffer since we cannot parse 647 * SILK packets and split it into individual frames. 633 648 */ 634 attr->info.max_bps *= 2; 649 attr->info.max_rx_frame_size = attr->info.max_bps * 650 attr->info.frm_ptime / 8 / 1000; 651 if ((attr->info.max_bps * attr->info.frm_ptime) % 8000 != 0) 652 { 653 ++attr->info.max_rx_frame_size; 654 } 655 attr->info.max_rx_frame_size *= SILK_MAX_FRAMES_PER_PACKET; 635 656 636 657 return PJ_SUCCESS; … … 722 743 { 723 744 silk_private *silk; 724 unsigned count; 745 SKP_Silk_TOC_struct toc; 746 unsigned i, count; 725 747 726 748 PJ_ASSERT_RETURN(codec && ts && frames && frame_cnt, PJ_EINVAL); 727 749 silk = (silk_private*)codec->codec_data; 728 750 729 PJ_TODO(support_parsing_multiple_frames_per_packet); 730 731 count = 0; 732 frames[count].type = PJMEDIA_FRAME_TYPE_AUDIO; 733 frames[count].buf = pkt; 734 frames[count].size = pkt_size; 735 frames[count].timestamp.u64 = ts->u64; 736 ++count; 751 SKP_Silk_SDK_get_TOC(pkt, pkt_size, &toc); 752 count = toc.framesInPacket; 753 pj_assert(count <= SILK_MAX_FRAMES_PER_PACKET); 754 755 for (i = 0; i < count; i++) { 756 frames[i].type = PJMEDIA_FRAME_TYPE_AUDIO; 757 frames[i].bit_info = (((unsigned)ts->u64 & 0xFFFF) << 16) | 758 (((unsigned)pkt & 0xFF) << 8) | i; 759 frames[i].buf = pkt; 760 frames[i].size = pkt_size; 761 frames[i].timestamp.u64 = ts->u64 + i * silk->samples_per_frame; 762 } 737 763 738 764 *frame_cnt = count; 739 765 return PJ_SUCCESS; 740 766 } 741 742 767 743 768 static pj_status_t silk_codec_decode(pjmedia_codec *codec, … … 748 773 silk_private *silk; 749 774 SKP_int16 out_size; 750 SKP_int err; 775 SKP_Silk_TOC_struct toc; 776 SKP_int err = 0; 777 unsigned pkt_info, frm_info; 751 778 752 779 PJ_ASSERT_RETURN(codec && input && output_buf_len && output, PJ_EINVAL); 753 780 silk = (silk_private*)codec->codec_data; 754 755 out_size = (SKP_int16)output_buf_len; 756 err = SKP_Silk_SDK_Decode(silk->dec_st, &silk->dec_ctl, 757 0, /* Normal frame flag */ 758 input->buf, 759 input->size, 760 output->buf, 761 &out_size); 762 if (err) { 763 PJ_LOG(3, (THIS_FILE, "Failed to decode frame (err=%d)", err)); 764 output->type = PJMEDIA_FRAME_TYPE_NONE; 765 output->buf = NULL; 766 output->size = 0; 767 return PJMEDIA_CODEC_EFAILED; 768 } 769 770 output->size = out_size; 771 output->type = PJMEDIA_FRAME_TYPE_AUDIO; 781 PJ_ASSERT_RETURN(output_buf_len >= silk->dec_buf_sz, PJ_ETOOSMALL); 782 783 SKP_Silk_SDK_get_TOC(input->buf, input->size, &toc); 784 pkt_info = input->bit_info & 0xFFFFFF00; 785 frm_info = input->bit_info & 0xF; 786 787 if (toc.framesInPacket == 0) { 788 output->size = 0; 789 } else if (silk->pkt_info != pkt_info || input->bit_info == 0) { 790 unsigned i; 791 SKP_int16 nsamples; 792 793 silk->pkt_info = pkt_info; 794 nsamples = (SKP_int16)silk->dec_buf_sz / silk->pcm_bytes_per_sample; 795 796 if (toc.framesInPacket-1 > (SKP_int)silk->dec_buf_cnt) { 797 /* Grow the buffer */ 798 for (i = silk->dec_buf_cnt+1; i < (unsigned)toc.framesInPacket; 799 i++) 800 { 801 silk->dec_buf[i-1] = pj_pool_alloc(silk->pool, 802 silk->dec_buf_sz); 803 } 804 silk->dec_buf_cnt = toc.framesInPacket-1; 805 } 806 807 /* We need to decode all the frames in the packet. */ 808 for (i = 0; i < (unsigned)toc.framesInPacket;) { 809 void *buf; 810 SKP_int16 *size; 811 812 if (i == 0 || i == frm_info) { 813 buf = output->buf; 814 size = &out_size; 815 } else { 816 buf = silk->dec_buf[i-1]; 817 size = &silk->dec_buf_size[i-1]; 818 } 819 820 *size = nsamples; 821 err = SKP_Silk_SDK_Decode(silk->dec_st, &silk->dec_ctl, 822 0, /* Normal frame flag */ 823 input->buf, input->size, 824 buf, size); 825 if (err) { 826 PJ_LOG(3, (THIS_FILE, "Failed to decode frame (err=%d)", 827 err)); 828 *size = 0; 829 } else { 830 *size = *size * silk->pcm_bytes_per_sample; 831 } 832 833 if (i == frm_info) { 834 output->size = *size; 835 } 836 837 i++; 838 if (!silk->dec_ctl.moreInternalDecoderFrames && 839 i < (unsigned)toc.framesInPacket) 840 { 841 /* It turns out that the packet does not have 842 * the number of frames as mentioned in the TOC. 843 */ 844 for (; i < (unsigned)toc.framesInPacket; i++) { 845 silk->dec_buf_size[i-1] = 0; 846 if (i == frm_info) { 847 output->size = 0; 848 } 849 } 850 } 851 } 852 } else { 853 /* We have already decoded this packet. */ 854 if (frm_info == 0 || silk->dec_buf_size[frm_info-1] == 0) { 855 /* The decoding was a failure. */ 856 output->size = 0; 857 } else { 858 /* Copy the decoded frame from the buffer. */ 859 pj_assert(frm_info-1 < silk->dec_buf_cnt); 860 if (frm_info-1 >= silk->dec_buf_cnt) { 861 output->size = 0; 862 } else { 863 pj_memcpy(output->buf, silk->dec_buf[frm_info-1], 864 silk->dec_buf_size[frm_info-1]); 865 output->size = silk->dec_buf_size[frm_info-1]; 866 } 867 } 868 } 869 870 if (output->size == 0) { 871 output->type = PJMEDIA_TYPE_NONE; 872 output->buf = NULL; 873 return PJMEDIA_CODEC_EFAILED; 874 } 875 876 output->type = PJMEDIA_TYPE_AUDIO; 772 877 output->timestamp = input->timestamp; 773 878 … … 780 885 */ 781 886 static pj_status_t silk_codec_recover(pjmedia_codec *codec, 782 unsigned output_buf_len,783 struct pjmedia_frame *output)887 unsigned output_buf_len, 888 struct pjmedia_frame *output) 784 889 { 785 890 silk_private *silk; … … 790 895 silk = (silk_private*)codec->codec_data; 791 896 792 out_size = (SKP_int16)output_buf_len ;897 out_size = (SKP_int16)output_buf_len / silk->pcm_bytes_per_sample; 793 898 err = SKP_Silk_SDK_Decode(silk->dec_st, &silk->dec_ctl, 794 899 1, /* Lost frame flag */ … … 805 910 } 806 911 807 output->size = out_size ;912 output->size = out_size * silk->pcm_bytes_per_sample; 808 913 output->type = PJMEDIA_FRAME_TYPE_AUDIO; 809 914
Note: See TracChangeset
for help on using the changeset viewer.