Esempio n. 1
0
OPUS_CUSTOM_NOSTATIC int opus_custom_decoder_init(CELTDecoder *st, const CELTMode *mode, int channels)
{
   if (channels < 0 || channels > 2)
      return OPUS_BAD_ARG;

   if (st==NULL)
      return OPUS_ALLOC_FAIL;

   OPUS_CLEAR((char*)st, opus_custom_decoder_get_size(mode, channels));

   st->mode = mode;
   st->overlap = mode->overlap;
   st->stream_channels = st->channels = channels;

   st->downsample = 1;
   st->start = 0;
   st->end = st->mode->effEBands;
   st->signalling = 1;
   st->arch = opus_select_arch();

   st->loss_count = 0;

   opus_custom_decoder_ctl(st, OPUS_RESET_STATE);

   return OPUS_OK;
}
Esempio n. 2
0
void tonality_analysis_reset(TonalityAnalysisState *tonal)
{
  /* Clear non-reusable fields. */
  char *start = (char*)&tonal->TONALITY_ANALYSIS_RESET_START;
  OPUS_CLEAR(start, sizeof(TonalityAnalysisState) - (start - (char*)tonal));
  tonal->music_confidence = .9f;
  tonal->speech_confidence = .1f;
}
Esempio n. 3
0
int opus_decoder_init(OpusDecoder *st, opus_int32 Fs, int channels)
{
   void *silk_dec;
   CELTDecoder *celt_dec;
   int ret, silkDecSizeBytes;

   if ((Fs!=48000&&Fs!=24000&&Fs!=16000&&Fs!=12000&&Fs!=8000)
    || (channels!=1&&channels!=2))
      return OPUS_BAD_ARG;

   OPUS_CLEAR((char*)st, opus_decoder_get_size(channels));
   /* Initialize SILK encoder */
   ret = silk_Get_Decoder_Size(&silkDecSizeBytes);
   if (ret)
      return OPUS_INTERNAL_ERROR;

   silkDecSizeBytes = align(silkDecSizeBytes);
   st->silk_dec_offset = align(sizeof(OpusDecoder));
   st->celt_dec_offset = st->silk_dec_offset+silkDecSizeBytes;
   silk_dec = (char*)st+st->silk_dec_offset;
   celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);
   st->stream_channels = st->channels = channels;

   st->Fs = Fs;
   st->DecControl.API_sampleRate = st->Fs;
   st->DecControl.nChannelsAPI      = st->channels;
   st->arch = opus_select_arch();

   /* Reset decoder */
   ret = silk_InitDecoder( silk_dec );
   if(ret)return OPUS_INTERNAL_ERROR;

   /* Initialize CELT decoder */
   ret = celt_decoder_init(celt_dec, Fs, channels);
   if(ret!=OPUS_OK)return OPUS_INTERNAL_ERROR;

   celt_decoder_ctl(celt_dec, CELT_SET_SIGNALLING(0));

   st->prev_mode = 0;
   st->frame_size = Fs/400;
   return OPUS_OK;
}
Esempio n. 4
0
static void opus_projection_copy_channel_out_short(
  void *dst,
  int dst_stride,
  int dst_channel,
  const opus_val16 *src,
  int src_stride,
  int frame_size,
  void *user_data)
{
  opus_int16 *short_dst;
  const MappingMatrix *matrix;
  short_dst = (opus_int16 *)dst;
  matrix = (const MappingMatrix *)user_data;
  if (dst_channel == 0)
    OPUS_CLEAR(short_dst, frame_size * dst_stride);

  if (src != NULL)
    mapping_matrix_multiply_channel_out_short(matrix, src, dst_channel,
      src_stride, short_dst, dst_stride, frame_size);
}
Esempio n. 5
0
int opus_decoder_ctl(OpusDecoder *st, int request, ...)
{
    int ret = OPUS_OK;
    va_list ap;
    void *silk_dec;
    CELTDecoder *celt_dec;

    silk_dec = (char*)st+st->silk_dec_offset;
    celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);


    va_start(ap, request);

    switch (request)
    {
    case OPUS_GET_BANDWIDTH_REQUEST:
    {
        opus_int32 *value = va_arg(ap, opus_int32*);
        if (!value)
        {
            goto bad_arg;
        }
        *value = st->bandwidth;
    }
    break;
    case OPUS_GET_FINAL_RANGE_REQUEST:
    {
        opus_uint32 *value = va_arg(ap, opus_uint32*);
        if (!value)
        {
            goto bad_arg;
        }
        *value = st->rangeFinal;
    }
    break;
    case OPUS_RESET_STATE:
    {
        OPUS_CLEAR((char*)&st->OPUS_DECODER_RESET_START,
                   sizeof(OpusDecoder)-
                   ((char*)&st->OPUS_DECODER_RESET_START - (char*)st));

        celt_decoder_ctl(celt_dec, OPUS_RESET_STATE);
        silk_InitDecoder( silk_dec );
        st->stream_channels = st->channels;
        st->frame_size = st->Fs/400;
    }
    break;
    case OPUS_GET_SAMPLE_RATE_REQUEST:
    {
        opus_int32 *value = va_arg(ap, opus_int32*);
        if (!value)
        {
            goto bad_arg;
        }
        *value = st->Fs;
    }
    break;
    case OPUS_GET_PITCH_REQUEST:
    {
        opus_int32 *value = va_arg(ap, opus_int32*);
        if (!value)
        {
            goto bad_arg;
        }
        if (st->prev_mode == MODE_CELT_ONLY)
            celt_decoder_ctl(celt_dec, OPUS_GET_PITCH(value));
        else
            *value = st->DecControl.prevPitchLag;
    }
    break;
    case OPUS_GET_GAIN_REQUEST:
    {
        opus_int32 *value = va_arg(ap, opus_int32*);
        if (!value)
        {
            goto bad_arg;
        }
        *value = st->decode_gain;
    }
    break;
    case OPUS_SET_GAIN_REQUEST:
    {
        opus_int32 value = va_arg(ap, opus_int32);
        if (value<-32768 || value>32767)
        {
            goto bad_arg;
        }
        st->decode_gain = value;
    }
    break;
    case OPUS_GET_LAST_PACKET_DURATION_REQUEST:
    {
        opus_uint32 *value = va_arg(ap, opus_uint32*);
        if (!value)
        {
            goto bad_arg;
        }
        *value = st->last_packet_duration;
    }
    break;
    default:
        /*fprintf(stderr, "unknown opus_decoder_ctl() request: %d", request);*/
        ret = OPUS_UNIMPLEMENTED;
        break;
    }

    va_end(ap);
    return ret;
bad_arg:
    va_end(ap);
    return OPUS_BAD_ARG;
}
Esempio n. 6
0
int opus_decoder_ctl(OpusDecoder *st, int request, ...)
{
   int ret = OPUS_OK;
   va_list ap;
   void *silk_dec;
   CELTDecoder *celt_dec;

   silk_dec = (char*)st+st->silk_dec_offset;
   celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);


   va_start(ap, request);

   switch (request)
   {
   case OPUS_GET_BANDWIDTH_REQUEST:
   {
      opus_int32 *value = va_arg(ap, opus_int32*);
      *value = st->bandwidth;
   }
   break;
   case OPUS_GET_FINAL_RANGE_REQUEST:
   {
      opus_uint32 *value = va_arg(ap, opus_uint32*);
      *value = st->rangeFinal;
   }
   break;
   case OPUS_RESET_STATE:
   {
      OPUS_CLEAR((char*)&st->OPUS_DECODER_RESET_START,
            sizeof(OpusDecoder)-
            ((char*)&st->OPUS_DECODER_RESET_START - (char*)st));

      celt_decoder_ctl(celt_dec, OPUS_RESET_STATE);
      silk_InitDecoder( silk_dec );
      st->stream_channels = st->channels;
      st->frame_size = st->Fs/400;
   }
   break;
   case OPUS_GET_PITCH_REQUEST:
   {
      int *value = va_arg(ap, opus_int32*);
      if (value==NULL)
      {
         ret = OPUS_BAD_ARG;
         break;
      }
      if (st->prev_mode == MODE_CELT_ONLY)
         celt_decoder_ctl(celt_dec, OPUS_GET_PITCH(value));
      else
         *value = st->DecControl.prevPitchLag;
   }
   break;
   default:
      /*fprintf(stderr, "unknown opus_decoder_ctl() request: %d", request);*/
      ret = OPUS_UNIMPLEMENTED;
      break;
   }

   va_end(ap);
   return ret;
}
Esempio n. 7
0
static int opus_multistream_encoder_init_impl(
      OpusMSEncoder *st,
      opus_int32 Fs,
      int channels,
      int streams,
      int coupled_streams,
      const unsigned char *mapping,
      int application,
      MappingType mapping_type
)
{
   int coupled_size;
   int mono_size;
   int i, ret;
   char *ptr;

   if ((channels>255) || (channels<1) || (coupled_streams>streams) ||
       (streams<1) || (coupled_streams<0) || (streams>255-coupled_streams))
      return OPUS_BAD_ARG;

   st->arch = opus_select_arch();
   st->layout.nb_channels = channels;
   st->layout.nb_streams = streams;
   st->layout.nb_coupled_streams = coupled_streams;
   if (mapping_type != MAPPING_TYPE_SURROUND)
      st->lfe_stream = -1;
   st->bitrate_bps = OPUS_AUTO;
   st->application = application;
   st->variable_duration = OPUS_FRAMESIZE_ARG;
   for (i=0;i<st->layout.nb_channels;i++)
      st->layout.mapping[i] = mapping[i];
   if (!validate_layout(&st->layout) || !validate_encoder_layout(&st->layout))
      return OPUS_BAD_ARG;
   ptr = (char*)st + align(sizeof(OpusMSEncoder));
   coupled_size = opus_encoder_get_size(2);
   mono_size = opus_encoder_get_size(1);

   for (i=0;i<st->layout.nb_coupled_streams;i++)
   {
      ret = opus_encoder_init((OpusEncoder*)ptr, Fs, 2, application);
      if(ret!=OPUS_OK)return ret;
      if (i==st->lfe_stream)
         opus_encoder_ctl((OpusEncoder*)ptr, OPUS_SET_LFE(1));
      ptr += align(coupled_size);
   }
   for (;i<st->layout.nb_streams;i++)
   {
      ret = opus_encoder_init((OpusEncoder*)ptr, Fs, 1, application);
      if (i==st->lfe_stream)
         opus_encoder_ctl((OpusEncoder*)ptr, OPUS_SET_LFE(1));
      if(ret!=OPUS_OK)return ret;
      ptr += align(mono_size);
   }
   if (mapping_type == MAPPING_TYPE_SURROUND)
   {
      OPUS_CLEAR(ms_get_preemph_mem(st), channels);
      OPUS_CLEAR(ms_get_window_mem(st), channels*120);
   }
   st->mapping_type = mapping_type;
   return OPUS_OK;
}
Esempio n. 8
0
void surround_analysis(const CELTMode *celt_mode, const void *pcm, opus_val16 *bandLogE, opus_val32 *mem, opus_val32 *preemph_mem,
      int len, int overlap, int channels, int rate, opus_copy_channel_in_func copy_channel_in, int arch
)
{
   int c;
   int i;
   int LM;
   int pos[8] = {0};
   int upsample;
   int frame_size;
   int freq_size;
   opus_val16 channel_offset;
   opus_val32 bandE[21];
   opus_val16 maskLogE[3][21];
   VARDECL(opus_val32, in);
   VARDECL(opus_val16, x);
   VARDECL(opus_val32, freq);
   SAVE_STACK;

   upsample = resampling_factor(rate);
   frame_size = len*upsample;
   freq_size = IMIN(960, frame_size);

   /* LM = log2(frame_size / 120) */
   for (LM=0;LM<celt_mode->maxLM;LM++)
      if (celt_mode->shortMdctSize<<LM==frame_size)
         break;

   ALLOC(in, frame_size+overlap, opus_val32);
   ALLOC(x, len, opus_val16);
   ALLOC(freq, freq_size, opus_val32);

   channel_pos(channels, pos);

   for (c=0;c<3;c++)
      for (i=0;i<21;i++)
         maskLogE[c][i] = -QCONST16(28.f, DB_SHIFT);

   for (c=0;c<channels;c++)
   {
      int frame;
      int nb_frames = frame_size/freq_size;
      celt_assert(nb_frames*freq_size == frame_size);
      OPUS_COPY(in, mem+c*overlap, overlap);
      (*copy_channel_in)(x, 1, pcm, channels, c, len);
      celt_preemphasis(x, in+overlap, frame_size, 1, upsample, celt_mode->preemph, preemph_mem+c, 0);
#ifndef FIXED_POINT
      {
         opus_val32 sum;
         sum = celt_inner_prod(in, in, frame_size+overlap, 0);
         /* This should filter out both NaNs and ridiculous signals that could
            cause NaNs further down. */
         if (!(sum < 1e9f) || celt_isnan(sum))
         {
            OPUS_CLEAR(in, frame_size+overlap);
            preemph_mem[c] = 0;
         }
      }
#endif
      OPUS_CLEAR(bandE, 21);
      for (frame=0;frame<nb_frames;frame++)
      {
         opus_val32 tmpE[21];
         clt_mdct_forward(&celt_mode->mdct, in+960*frame, freq, celt_mode->window,
               overlap, celt_mode->maxLM-LM, 1, arch);
         if (upsample != 1)
         {
            int bound = freq_size/upsample;
            for (i=0;i<bound;i++)
               freq[i] *= upsample;
            for (;i<freq_size;i++)
               freq[i] = 0;
         }

         compute_band_energies(celt_mode, freq, tmpE, 21, 1, LM);
         /* If we have multiple frames, take the max energy. */
         for (i=0;i<21;i++)
            bandE[i] = MAX32(bandE[i], tmpE[i]);
      }
      amp2Log2(celt_mode, 21, 21, bandE, bandLogE+21*c, 1);
      /* Apply spreading function with -6 dB/band going up and -12 dB/band going down. */
      for (i=1;i<21;i++)
         bandLogE[21*c+i] = MAX16(bandLogE[21*c+i], bandLogE[21*c+i-1]-QCONST16(1.f, DB_SHIFT));
      for (i=19;i>=0;i--)
         bandLogE[21*c+i] = MAX16(bandLogE[21*c+i], bandLogE[21*c+i+1]-QCONST16(2.f, DB_SHIFT));
      if (pos[c]==1)
      {
         for (i=0;i<21;i++)
            maskLogE[0][i] = logSum(maskLogE[0][i], bandLogE[21*c+i]);
      } else if (pos[c]==3)
      {
         for (i=0;i<21;i++)
            maskLogE[2][i] = logSum(maskLogE[2][i], bandLogE[21*c+i]);
      } else if (pos[c]==2)
      {
         for (i=0;i<21;i++)
         {
            maskLogE[0][i] = logSum(maskLogE[0][i], bandLogE[21*c+i]-QCONST16(.5f, DB_SHIFT));
            maskLogE[2][i] = logSum(maskLogE[2][i], bandLogE[21*c+i]-QCONST16(.5f, DB_SHIFT));
         }
      }
#if 0
      for (i=0;i<21;i++)
         printf("%f ", bandLogE[21*c+i]);
      float sum=0;
      for (i=0;i<21;i++)
         sum += bandLogE[21*c+i];
      printf("%f ", sum/21);
#endif
      OPUS_COPY(mem+c*overlap, in+frame_size, overlap);
   }
   for (i=0;i<21;i++)
      maskLogE[1][i] = MIN32(maskLogE[0][i],maskLogE[2][i]);
   channel_offset = HALF16(celt_log2(QCONST32(2.f,14)/(channels-1)));
   for (c=0;c<3;c++)
      for (i=0;i<21;i++)
         maskLogE[c][i] += channel_offset;
#if 0
   for (c=0;c<3;c++)
   {
      for (i=0;i<21;i++)
         printf("%f ", maskLogE[c][i]);
   }
#endif
   for (c=0;c<channels;c++)
   {
      opus_val16 *mask;
      if (pos[c]!=0)
      {
         mask = &maskLogE[pos[c]-1][0];
         for (i=0;i<21;i++)
            bandLogE[21*c+i] = bandLogE[21*c+i] - mask[i];
      } else {
         for (i=0;i<21;i++)
            bandLogE[21*c+i] = 0;
      }
#if 0
      for (i=0;i<21;i++)
         printf("%f ", bandLogE[21*c+i]);
      printf("\n");
#endif
#if 0
      float sum=0;
      for (i=0;i<21;i++)
         sum += bandLogE[21*c+i];
      printf("%f ", sum/(float)QCONST32(21.f, DB_SHIFT));
      printf("\n");
#endif
   }
   RESTORE_STACK;
}