1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133
|
#include "RARAudioDecoder.h"
#include <stdint.h>
#include <string.h>
static inline int iabs(int x) { return x<0?-x:x; }
int DecodeRAR20Audio(RAR20AudioState *state,int *channeldelta,int delta)
{
state->count++;
state->delta4=state->delta3;
state->delta3=state->delta2;
state->delta2=state->lastdelta-state->delta1;
state->delta1=state->lastdelta;
int predbyte=((
8*state->lastbyte+
state->weight1*state->delta1+
state->weight2*state->delta2+
state->weight3*state->delta3+
state->weight4*state->delta4+
state->weight5**channeldelta
)>>3)&0xff;
int byte=predbyte-delta&0xff;
int prederror=((int8_t)delta)<<3;
state->error[0]+=iabs(prederror);
state->error[1]+=iabs(prederror-state->delta1);
state->error[2]+=iabs(prederror+state->delta1);
state->error[3]+=iabs(prederror-state->delta2);
state->error[4]+=iabs(prederror+state->delta2);
state->error[5]+=iabs(prederror-state->delta3);
state->error[6]+=iabs(prederror+state->delta3);
state->error[7]+=iabs(prederror-state->delta4);
state->error[8]+=iabs(prederror+state->delta4);
state->error[9]+=iabs(prederror-*channeldelta);
state->error[10]+=iabs(prederror+*channeldelta);
*channeldelta=state->lastdelta=(int8_t)(byte-state->lastbyte);
state->lastbyte=byte;
if((state->count&0x1f)==0)
{
int minerror=state->error[0];
int minindex=0;
for(int i=1;i<11;i++)
{
if(state->error[i]<minerror)
{
minerror=state->error[i];
minindex=i;
}
}
memset(state->error,0,sizeof(state->error));
switch(minindex)
{
case 1: if(state->weight1>=-16) state->weight1--; break;
case 2: if(state->weight1<16) state->weight1++; break;
case 3: if(state->weight2>=-16) state->weight2--; break;
case 4: if(state->weight2<16) state->weight2++; break;
case 5: if(state->weight3>=-16) state->weight3--; break;
case 6: if(state->weight3<16) state->weight3++; break;
case 7: if(state->weight4>=-16) state->weight4--; break;
case 8: if(state->weight4<16) state->weight4++; break;
case 9: if(state->weight5>=-16) state->weight5--; break;
case 10: if(state->weight5<16) state->weight5++; break;
}
}
return byte;
}
int DecodeRAR30Audio(RAR30AudioState *state,int delta)
{
state->delta3=state->delta2;
state->delta2=state->lastdelta-state->delta1;
state->delta1=state->lastdelta;
int predbyte=((
8*state->lastbyte+
state->weight1*state->delta1+
state->weight2*state->delta2+
state->weight3*state->delta3
)>>3)&0xff;
int byte=predbyte-delta&0xff;
int prederror=((int8_t)delta)<<3;
state->error[0]+=iabs(prederror);
state->error[1]+=iabs(prederror-state->delta1);
state->error[2]+=iabs(prederror+state->delta1);
state->error[3]+=iabs(prederror-state->delta2);
state->error[4]+=iabs(prederror+state->delta2);
state->error[5]+=iabs(prederror-state->delta3);
state->error[6]+=iabs(prederror+state->delta3);
state->lastdelta=(int8_t)(byte-state->lastbyte);
state->lastbyte=byte;
if((state->count&0x1f)==0)
{
int minerror=state->error[0];
int minindex=0;
for(int i=1;i<7;i++)
{
if(state->error[i]<minerror)
{
minerror=state->error[i];
minindex=i;
}
}
memset(state->error,0,sizeof(state->error));
switch(minindex)
{
case 1: if(state->weight1>=-16) state->weight1--; break;
case 2: if(state->weight1<16) state->weight1++; break;
case 3: if(state->weight2>=-16) state->weight2--; break;
case 4: if(state->weight2<16) state->weight2++; break;
case 5: if(state->weight3>=-16) state->weight3--; break;
case 6: if(state->weight3<16) state->weight3++; break;
}
}
state->count++;
return byte;
}
|