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; }
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; }