LCOV - code coverage report
Current view: top level - media/libopus/src - opus.c (source / functions) Hit Total Coverage
Test: output.info Lines: 0 175 0.0 %
Date: 2017-07-14 16:53:18 Functions: 0 6 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* Copyright (c) 2011 Xiph.Org Foundation, Skype Limited
       2             :    Written by Jean-Marc Valin and Koen Vos */
       3             : /*
       4             :    Redistribution and use in source and binary forms, with or without
       5             :    modification, are permitted provided that the following conditions
       6             :    are met:
       7             : 
       8             :    - Redistributions of source code must retain the above copyright
       9             :    notice, this list of conditions and the following disclaimer.
      10             : 
      11             :    - Redistributions in binary form must reproduce the above copyright
      12             :    notice, this list of conditions and the following disclaimer in the
      13             :    documentation and/or other materials provided with the distribution.
      14             : 
      15             :    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
      16             :    ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
      17             :    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
      18             :    A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
      19             :    OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
      20             :    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
      21             :    PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
      22             :    PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
      23             :    LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
      24             :    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
      25             :    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
      26             : */
      27             : 
      28             : #ifdef HAVE_CONFIG_H
      29             : #include "config.h"
      30             : #endif
      31             : 
      32             : #include "opus.h"
      33             : #include "opus_private.h"
      34             : 
      35             : #ifndef DISABLE_FLOAT_API
      36           0 : OPUS_EXPORT void opus_pcm_soft_clip(float *_x, int N, int C, float *declip_mem)
      37             : {
      38             :    int c;
      39             :    int i;
      40             :    float *x;
      41             : 
      42           0 :    if (C<1 || N<1 || !_x || !declip_mem) return;
      43             : 
      44             :    /* First thing: saturate everything to +/- 2 which is the highest level our
      45             :       non-linearity can handle. At the point where the signal reaches +/-2,
      46             :       the derivative will be zero anyway, so this doesn't introduce any
      47             :       discontinuity in the derivative. */
      48           0 :    for (i=0;i<N*C;i++)
      49           0 :       _x[i] = MAX16(-2.f, MIN16(2.f, _x[i]));
      50           0 :    for (c=0;c<C;c++)
      51             :    {
      52             :       float a;
      53             :       float x0;
      54             :       int curr;
      55             : 
      56           0 :       x = _x+c;
      57           0 :       a = declip_mem[c];
      58             :       /* Continue applying the non-linearity from the previous frame to avoid
      59             :          any discontinuity. */
      60           0 :       for (i=0;i<N;i++)
      61             :       {
      62           0 :          if (x[i*C]*a>=0)
      63           0 :             break;
      64           0 :          x[i*C] = x[i*C]+a*x[i*C]*x[i*C];
      65             :       }
      66             : 
      67           0 :       curr=0;
      68           0 :       x0 = x[0];
      69             :       while(1)
      70           0 :       {
      71             :          int start, end;
      72             :          float maxval;
      73           0 :          int special=0;
      74             :          int peak_pos;
      75           0 :          for (i=curr;i<N;i++)
      76             :          {
      77           0 :             if (x[i*C]>1 || x[i*C]<-1)
      78             :                break;
      79             :          }
      80           0 :          if (i==N)
      81             :          {
      82           0 :             a=0;
      83           0 :             break;
      84             :          }
      85           0 :          peak_pos = i;
      86           0 :          start=end=i;
      87           0 :          maxval=ABS16(x[i*C]);
      88             :          /* Look for first zero crossing before clipping */
      89           0 :          while (start>0 && x[i*C]*x[(start-1)*C]>=0)
      90           0 :             start--;
      91             :          /* Look for first zero crossing after clipping */
      92           0 :          while (end<N && x[i*C]*x[end*C]>=0)
      93             :          {
      94             :             /* Look for other peaks until the next zero-crossing. */
      95           0 :             if (ABS16(x[end*C])>maxval)
      96             :             {
      97           0 :                maxval = ABS16(x[end*C]);
      98           0 :                peak_pos = end;
      99             :             }
     100           0 :             end++;
     101             :          }
     102             :          /* Detect the special case where we clip before the first zero crossing */
     103           0 :          special = (start==0 && x[i*C]*x[0]>=0);
     104             : 
     105             :          /* Compute a such that maxval + a*maxval^2 = 1 */
     106           0 :          a=(maxval-1)/(maxval*maxval);
     107             :          /* Slightly boost "a" by 2^-22. This is just enough to ensure -ffast-math
     108             :             does not cause output values larger than +/-1, but small enough not
     109             :             to matter even for 24-bit output.  */
     110           0 :          a += a*2.4e-7f;
     111           0 :          if (x[i*C]>0)
     112           0 :             a = -a;
     113             :          /* Apply soft clipping */
     114           0 :          for (i=start;i<end;i++)
     115           0 :             x[i*C] = x[i*C]+a*x[i*C]*x[i*C];
     116             : 
     117           0 :          if (special && peak_pos>=2)
     118             :          {
     119             :             /* Add a linear ramp from the first sample to the signal peak.
     120             :                This avoids a discontinuity at the beginning of the frame. */
     121             :             float delta;
     122           0 :             float offset = x0-x[0];
     123           0 :             delta = offset / peak_pos;
     124           0 :             for (i=curr;i<peak_pos;i++)
     125             :             {
     126           0 :                offset -= delta;
     127           0 :                x[i*C] += offset;
     128           0 :                x[i*C] = MAX16(-1.f, MIN16(1.f, x[i*C]));
     129             :             }
     130             :          }
     131           0 :          curr = end;
     132           0 :          if (curr==N)
     133           0 :             break;
     134             :       }
     135           0 :       declip_mem[c] = a;
     136             :    }
     137             : }
     138             : #endif
     139             : 
     140           0 : int encode_size(int size, unsigned char *data)
     141             : {
     142           0 :    if (size < 252)
     143             :    {
     144           0 :       data[0] = size;
     145           0 :       return 1;
     146             :    } else {
     147           0 :       data[0] = 252+(size&0x3);
     148           0 :       data[1] = (size-(int)data[0])>>2;
     149           0 :       return 2;
     150             :    }
     151             : }
     152             : 
     153           0 : static int parse_size(const unsigned char *data, opus_int32 len, opus_int16 *size)
     154             : {
     155           0 :    if (len<1)
     156             :    {
     157           0 :       *size = -1;
     158           0 :       return -1;
     159           0 :    } else if (data[0]<252)
     160             :    {
     161           0 :       *size = data[0];
     162           0 :       return 1;
     163           0 :    } else if (len<2)
     164             :    {
     165           0 :       *size = -1;
     166           0 :       return -1;
     167             :    } else {
     168           0 :       *size = 4*data[1] + data[0];
     169           0 :       return 2;
     170             :    }
     171             : }
     172             : 
     173           0 : int opus_packet_get_samples_per_frame(const unsigned char *data,
     174             :       opus_int32 Fs)
     175             : {
     176             :    int audiosize;
     177           0 :    if (data[0]&0x80)
     178             :    {
     179           0 :       audiosize = ((data[0]>>3)&0x3);
     180           0 :       audiosize = (Fs<<audiosize)/400;
     181           0 :    } else if ((data[0]&0x60) == 0x60)
     182             :    {
     183           0 :       audiosize = (data[0]&0x08) ? Fs/50 : Fs/100;
     184             :    } else {
     185           0 :       audiosize = ((data[0]>>3)&0x3);
     186           0 :       if (audiosize == 3)
     187           0 :          audiosize = Fs*60/1000;
     188             :       else
     189           0 :          audiosize = (Fs<<audiosize)/100;
     190             :    }
     191           0 :    return audiosize;
     192             : }
     193             : 
     194           0 : int opus_packet_parse_impl(const unsigned char *data, opus_int32 len,
     195             :       int self_delimited, unsigned char *out_toc,
     196             :       const unsigned char *frames[48], opus_int16 size[48],
     197             :       int *payload_offset, opus_int32 *packet_offset)
     198             : {
     199             :    int i, bytes;
     200             :    int count;
     201             :    int cbr;
     202             :    unsigned char ch, toc;
     203             :    int framesize;
     204             :    opus_int32 last_size;
     205           0 :    opus_int32 pad = 0;
     206           0 :    const unsigned char *data0 = data;
     207             : 
     208           0 :    if (size==NULL || len<0)
     209           0 :       return OPUS_BAD_ARG;
     210           0 :    if (len==0)
     211           0 :       return OPUS_INVALID_PACKET;
     212             : 
     213           0 :    framesize = opus_packet_get_samples_per_frame(data, 48000);
     214             : 
     215           0 :    cbr = 0;
     216           0 :    toc = *data++;
     217           0 :    len--;
     218           0 :    last_size = len;
     219           0 :    switch (toc&0x3)
     220             :    {
     221             :    /* One frame */
     222             :    case 0:
     223           0 :       count=1;
     224           0 :       break;
     225             :    /* Two CBR frames */
     226             :    case 1:
     227           0 :       count=2;
     228           0 :       cbr = 1;
     229           0 :       if (!self_delimited)
     230             :       {
     231           0 :          if (len&0x1)
     232           0 :             return OPUS_INVALID_PACKET;
     233           0 :          last_size = len/2;
     234             :          /* If last_size doesn't fit in size[0], we'll catch it later */
     235           0 :          size[0] = (opus_int16)last_size;
     236             :       }
     237           0 :       break;
     238             :    /* Two VBR frames */
     239             :    case 2:
     240           0 :       count = 2;
     241           0 :       bytes = parse_size(data, len, size);
     242           0 :       len -= bytes;
     243           0 :       if (size[0]<0 || size[0] > len)
     244           0 :          return OPUS_INVALID_PACKET;
     245           0 :       data += bytes;
     246           0 :       last_size = len-size[0];
     247           0 :       break;
     248             :    /* Multiple CBR/VBR frames (from 0 to 120 ms) */
     249             :    default: /*case 3:*/
     250           0 :       if (len<1)
     251           0 :          return OPUS_INVALID_PACKET;
     252             :       /* Number of frames encoded in bits 0 to 5 */
     253           0 :       ch = *data++;
     254           0 :       count = ch&0x3F;
     255           0 :       if (count <= 0 || framesize*count > 5760)
     256           0 :          return OPUS_INVALID_PACKET;
     257           0 :       len--;
     258             :       /* Padding flag is bit 6 */
     259           0 :       if (ch&0x40)
     260             :       {
     261             :          int p;
     262             :          do {
     263             :             int tmp;
     264           0 :             if (len<=0)
     265           0 :                return OPUS_INVALID_PACKET;
     266           0 :             p = *data++;
     267           0 :             len--;
     268           0 :             tmp = p==255 ? 254: p;
     269           0 :             len -= tmp;
     270           0 :             pad += tmp;
     271           0 :          } while (p==255);
     272             :       }
     273           0 :       if (len<0)
     274           0 :          return OPUS_INVALID_PACKET;
     275             :       /* VBR flag is bit 7 */
     276           0 :       cbr = !(ch&0x80);
     277           0 :       if (!cbr)
     278             :       {
     279             :          /* VBR case */
     280           0 :          last_size = len;
     281           0 :          for (i=0;i<count-1;i++)
     282             :          {
     283           0 :             bytes = parse_size(data, len, size+i);
     284           0 :             len -= bytes;
     285           0 :             if (size[i]<0 || size[i] > len)
     286           0 :                return OPUS_INVALID_PACKET;
     287           0 :             data += bytes;
     288           0 :             last_size -= bytes+size[i];
     289             :          }
     290           0 :          if (last_size<0)
     291           0 :             return OPUS_INVALID_PACKET;
     292           0 :       } else if (!self_delimited)
     293             :       {
     294             :          /* CBR case */
     295           0 :          last_size = len/count;
     296           0 :          if (last_size*count!=len)
     297           0 :             return OPUS_INVALID_PACKET;
     298           0 :          for (i=0;i<count-1;i++)
     299           0 :             size[i] = (opus_int16)last_size;
     300             :       }
     301           0 :       break;
     302             :    }
     303             :    /* Self-delimited framing has an extra size for the last frame. */
     304           0 :    if (self_delimited)
     305             :    {
     306           0 :       bytes = parse_size(data, len, size+count-1);
     307           0 :       len -= bytes;
     308           0 :       if (size[count-1]<0 || size[count-1] > len)
     309           0 :          return OPUS_INVALID_PACKET;
     310           0 :       data += bytes;
     311             :       /* For CBR packets, apply the size to all the frames. */
     312           0 :       if (cbr)
     313             :       {
     314           0 :          if (size[count-1]*count > len)
     315           0 :             return OPUS_INVALID_PACKET;
     316           0 :          for (i=0;i<count-1;i++)
     317           0 :             size[i] = size[count-1];
     318           0 :       } else if (bytes+size[count-1] > last_size)
     319           0 :          return OPUS_INVALID_PACKET;
     320             :    } else
     321             :    {
     322             :       /* Because it's not encoded explicitly, it's possible the size of the
     323             :          last packet (or all the packets, for the CBR case) is larger than
     324             :          1275. Reject them here.*/
     325           0 :       if (last_size > 1275)
     326           0 :          return OPUS_INVALID_PACKET;
     327           0 :       size[count-1] = (opus_int16)last_size;
     328             :    }
     329             : 
     330           0 :    if (payload_offset)
     331           0 :       *payload_offset = (int)(data-data0);
     332             : 
     333           0 :    for (i=0;i<count;i++)
     334             :    {
     335           0 :       if (frames)
     336           0 :          frames[i] = data;
     337           0 :       data += size[i];
     338             :    }
     339             : 
     340           0 :    if (packet_offset)
     341           0 :       *packet_offset = pad+(opus_int32)(data-data0);
     342             : 
     343           0 :    if (out_toc)
     344           0 :       *out_toc = toc;
     345             : 
     346           0 :    return count;
     347             : }
     348             : 
     349           0 : int opus_packet_parse(const unsigned char *data, opus_int32 len,
     350             :       unsigned char *out_toc, const unsigned char *frames[48],
     351             :       opus_int16 size[48], int *payload_offset)
     352             : {
     353           0 :    return opus_packet_parse_impl(data, len, 0, out_toc,
     354             :                                  frames, size, payload_offset, NULL);
     355             : }
     356             : 

Generated by: LCOV version 1.13