Pastebin launched a little side project called VERYVIRAL.com, check it out ;-) Want more features on Pastebin? Sign Up, it's FREE!
Guest

Experimental BCn-like Block-Audio Codec

By: cr88192 on Apr 23rd, 2013  |  syntax: C  |  size: 8.26 KB  |  views: 28  |  expires: Never
download  |  raw  |  embed  |  report abuse  |  print
Text below is selected. Please press Ctrl+C to copy to your clipboard. (⌘+C on Mac)
  1. /*
  2. Copyright (C) 2013 by Brendan G Bohannon
  3. Email: cr88192@gmail.com
  4. Copying: http://pastebin.com/iJxtZHm6
  5.  */
  6.  
  7. /*
  8. Experimental block-based audio codec.
  9. Encodes blocks of 64 samples into 256 bits (32 bytes).
  10. At 44.1kHz this is 176kbps.
  11. It can encode stereo using a "naive joint stereo" encoding.
  12.  
  13. Basic Format:
  14.     16 bit min sample (center)
  15.     16 bit max sample (center)
  16.     8 bit left-center min (truncated)
  17.     8 bit left-center max
  18.     currently unused (16 bits)
  19.     64 Samples, 1 bits/sample (64 bits)
  20.     16x 4-bit min (64 bits)
  21.     16x 4-bit max (64 bits)
  22.  
  23. The 4-bit values interpolate between the full min/max for the block.
  24. The 1-bit samples select between the min and max value for each sample.
  25.  
  26. Note: Interpolated values are linear, thus 0=0/15, 1=1/15, 2=2/15, ..., 14=14/15, 15=15/15
  27.  
  28. Bit packing is in low-high order, and multibyte values are little-endian.
  29.  */
  30.  
  31. #include <bgbtac.h>
  32.  
  33. void BGBTAC_EncodeBlock8MonoS16(s16 *iblk, byte *oblk)
  34. {
  35.         int tcma[16], tcna[16];
  36.         int tcmb[16], tcnb[16];
  37.         int lm, ln, cm, rm, rn, cn, tl, tr, tc;
  38.         int cm2, cn2, ca2;
  39.         int p0, p1, p2, p3;
  40.         int s0, s1;
  41.         int i, j, k;
  42.  
  43.         lm= 99999; rm= 99999; cm= 99999;
  44.         ln=-99999; rn=-99999; cn=-99999;
  45.        
  46.         for(i=0; i<64; i++)
  47.         {
  48.                 tl=iblk[i]; tr=tl;
  49.                 k=(tl+tr)>>1;
  50.                 if(k<cm) { lm=tl; rm=tr; cm=k; }
  51.                 if(k>cn) { ln=tl; rn=tr; cn=k; }
  52.         }
  53.        
  54.         for(i=0; i<32; i++)
  55.                 { oblk[i]=0; }
  56.        
  57.         oblk[0]=cm&0xFF;
  58.         oblk[1]=(cm>>8)&0xFF;
  59.         oblk[2]=cn&0xFF;
  60.         oblk[3]=(cn>>8)&0xFF;
  61.         oblk[4]=((lm-rm+128)>>8)&0xFF;
  62.         oblk[5]=((ln-rn+128)>>8)&0xFF;
  63.        
  64.         for(i=0; i<16; i++)
  65.         {
  66.                 cm2= 99999; cn2=-99999;
  67.                 for(j=0; j<4; j++)
  68.                 {
  69.                         tl=iblk[i*4+j]; tr=tl;
  70.                         tc=(tl+tr)>>1;
  71.                         if(tc<cm2) { cm2=tc; }
  72.                         if(tc>cn2) { cn2=tc; }
  73.                 }
  74.                
  75.                 if(cn!=cm)
  76.                         { s0=16777216/(cn-cm); }
  77.                 else { s0=0; }
  78.  
  79.                 p0=(s0*(cm2-cm)+524288)>>20;
  80.                 p1=(s0*(cn2-cm)+524288)>>20;
  81.                
  82.                 p0=(p0<0)?0:((p0<16)?p0:15);
  83.                 p1=(p1<0)?0:((p1<16)?p1:15);
  84.                
  85.                 tcma[i]=p0;
  86.                 tcna[i]=p1;
  87.  
  88.                 s1=(cn-cm);
  89.                 cm2=((s1*p0+8)>>4)+cm;
  90.                 cn2=((s1*p1+8)>>4)+cm;
  91.  
  92.                 tcmb[i]=cm2;
  93.                 tcnb[i]=cn2;
  94.         }
  95.  
  96.         for(i=0; i<16; i++)
  97.         {
  98.                 oblk[16+(i>>1)]|=tcma[i]<<((i&1)*4);
  99.                 oblk[24+(i>>1)]|=tcna[i]<<((i&1)*4);
  100.         }
  101.        
  102.         for(i=0; i<16; i++)
  103.         {
  104.                 ca2=(tcmb[i]+tcnb[i])>>1;
  105.        
  106.                 for(j=0; j<4; j++)
  107.                 {
  108.                         k=i*4+j;
  109.                
  110.                         tl=iblk[k]; tr=tl;
  111. //                      tl=(iblk[k]+7)>>4; tr=tl;
  112.                         tc=(tl+tr)>>1;
  113.  
  114.                         if(tc>=ca2)
  115.                                 { oblk[8+(k>>3)]|=1<<(k&7); }
  116.                         else
  117.                                 { oblk[8+(k>>3)]&=~(1<<(k&7)); }
  118.                 }
  119.         }      
  120. }
  121.  
  122. void BGBTAC_DecodeBlock8MonoS16(byte *iblk, s16 *oblk)
  123. {
  124.         int tcma[16], tcna[16];
  125.         int tcmb[16], tcnb[16];
  126.         int p0, p1, p2, p3;
  127.         int cm, cn, ca;
  128.         int cm2, cn2, ca2;
  129.         int i, j, k;
  130.        
  131.         cm=(s16)(iblk[0]+(iblk[1]<<8));
  132.         cn=(s16)(iblk[2]+(iblk[3]<<8));
  133.         ca=(cm+cn)>>1;
  134.  
  135.         for(i=0; i<128; i++)
  136.                 { oblk[i]=ca; }
  137.                
  138.         for(i=0; i<16; i++)
  139.         {
  140.                 cm2=(iblk[16+(i>>1)]>>((i&1)*4))&15;
  141.                 cn2=(iblk[24+(i>>1)]>>((i&1)*4))&15;
  142. //              cm2=tcmb[i];
  143. //              cn2=tcnb[i];
  144.        
  145.                 j=(cn-cm);
  146.                 p0=((j*cm2+8)>>4)+cm;
  147.                 p1=((j*cn2+8)>>4)+cm;
  148.  
  149.                 p0=(p0<cm)?cm:((p0<cn)?p0:cn);
  150.                 p1=(p1<cm)?cm:((p1<cn)?p1:cn);
  151.        
  152.                 tcma[i]=p0;
  153.                 tcna[i]=p1;
  154.                
  155.                 p2=(p0+p1)>>1;
  156. //              if(p2<cm)p2=cm;
  157. //              if(p2>cn)p2=cn;
  158.                
  159.                 for(j=0; j<4; j++)
  160.                 {
  161.                         k=i*4+j;
  162.                
  163. //                      oblk[i*16+j]=p2;
  164.                         oblk[i*4+j]=(iblk[8+(k>>3)]&(1<<(k&7)))?p1:p0;
  165.                 }
  166.         }
  167. }
  168.  
  169. BTAC_API void BGBTAC_EncodeStream8MonoS16(s16 *iblk, byte *oblk, int len)
  170. {
  171.         int i, j, n;
  172.        
  173.         n=(len+63)/64;
  174.         for(i=0; i<n; i++)
  175.         {
  176.                 BGBTAC_EncodeBlock8MonoS16(iblk+i*64, oblk+i*32);
  177.         }
  178. }
  179.  
  180. BTAC_API void BGBTAC_DecodeStream8MonoS16(byte *iblk, s16 *oblk, int len)
  181. {
  182.         int i, j, n;
  183.        
  184.         n=(len+63)/64;
  185.         for(i=0; i<n; i++)
  186.         {
  187.                 BGBTAC_DecodeBlock8MonoS16(iblk+i*32, oblk+i*64);
  188.         }
  189. }
  190.  
  191.  
  192.  
  193. void BGBTAC_EncodeBlock8StereoS16(s16 *iblk, byte *oblk)
  194. {
  195.         s16 tcblk[64];
  196.         int tcma[16], tcna[16];
  197.         int tcmb[16], tcnb[16];
  198.         int lm, ln, cm, rm, rn, cn, tl, tr, tc;
  199.         int cm2, cn2, ca2, ba;
  200.         int p0, p1, p2, p3;
  201.         int s0, s1;
  202.         int i, j, k;
  203.  
  204.         lm= 99999; rm= 99999; cm= 99999;
  205.         ln=-99999; rn=-99999; cn=-99999;
  206.        
  207.         ba=0;
  208.         for(i=0; i<64; i++)
  209.         {
  210.                 tl=iblk[i*2+0];
  211.                 tr=iblk[i*2+1];
  212.                 k=(tl+tr)>>1;
  213.                 tcblk[i]=k;
  214.                 ba+=tl-k;
  215.                 if(k<cm) { lm=tl; rm=tr; cm=k; }
  216.                 if(k>cn) { ln=tl; rn=tr; cn=k; }
  217.         }
  218.  
  219.         ba/=64;
  220.        
  221.         for(i=0; i<32; i++)
  222.                 { oblk[i]=0; }
  223.  
  224.        
  225.         p0=(lm-cm+128)>>8;
  226.         p1=(ln-cn+128)>>8;
  227.         p2=(ba+128)>>8;
  228.         p0=(5*p0+11*p2)>>4;
  229.         p1=(5*p1+11*p2)>>4;
  230. //      p0=p2; p1=p2;
  231.  
  232.         p0=(p0<0)?0:((p0<256)?p0:255);
  233.         p1=(p1<0)?0:((p1<256)?p1:255);
  234.        
  235.         oblk[0]=cm&0xFF;
  236.         oblk[1]=(cm>>8)&0xFF;
  237.         oblk[2]=cn&0xFF;
  238.         oblk[3]=(cn>>8)&0xFF;
  239. //      oblk[4]=((lm-cm+128)>>8)&0xFF;
  240. //      oblk[5]=((ln-cn+128)>>8)&0xFF;
  241.  
  242.         oblk[4]=p0&0xFF;
  243.         oblk[5]=p1&0xFF;
  244.        
  245.         for(i=0; i<16; i++)
  246.         {
  247.                 cm2= 99999; cn2=-99999;
  248.                 for(j=0; j<4; j++)
  249.                 {
  250.                         tc=tcblk[i*4+j];
  251.                         if(tc<cm2) { cm2=tc; }
  252.                         if(tc>cn2) { cn2=tc; }
  253.                 }
  254.                
  255.                 if(cn!=cm)
  256.                         { s0=16777216/(cn-cm); }
  257.                 else { s0=0; }
  258.  
  259.                 p0=(s0*(cm2-cm)+524288)>>20;
  260.                 p1=(s0*(cn2-cm)+524288)>>20;
  261.  
  262. //              p0=(s0*(cm2-cm)+262144)>>20;
  263. //              p1=(s0*(cn2-cm)+786432)>>20;
  264.                
  265.                 p0=(p0<0)?0:((p0<16)?p0:15);
  266.                 p1=(p1<0)?0:((p1<16)?p1:15);
  267.                
  268.                 tcma[i]=p0;
  269.                 tcna[i]=p1;
  270.  
  271.                 s1=(cn-cm);
  272.                 cm2=((s1*p0+8)>>4)+cm;
  273.                 cn2=((s1*p1+8)>>4)+cm;
  274.  
  275.                 tcmb[i]=cm2;
  276.                 tcnb[i]=cn2;
  277.         }
  278.  
  279.         for(i=0; i<16; i++)
  280.         {
  281.                 oblk[16+(i>>1)]|=tcma[i]<<((i&1)*4);
  282.                 oblk[24+(i>>1)]|=tcna[i]<<((i&1)*4);
  283.         }
  284.        
  285.         for(i=0; i<16; i++)
  286.         {
  287.                 ca2=(tcmb[i]+tcnb[i])>>1;
  288.        
  289.                 for(j=0; j<4; j++)
  290.                 {
  291.                         k=i*4+j;
  292.                         tc=tcblk[k];
  293.                         if(tc>=ca2)
  294.                                 { oblk[8+(k>>3)]|=1<<(k&7); }
  295.                         else
  296.                                 { oblk[8+(k>>3)]&=~(1<<(k&7)); }
  297.                 }
  298.         }      
  299. }
  300.  
  301. void BGBTAC_DecodeBlock8StereoS16(byte *iblk, s16 *oblk)
  302. {
  303. //      int tcma[16], tcna[16];
  304. //      int tcmb[16], tcnb[16];
  305.         int p0, p1, p2, p3;
  306.         int s0, s1;
  307.         int cm, cn, ca;
  308.         int lm, ln, la;
  309.         int rm, rn, ra;
  310.         int cm2, cn2, ca2;
  311.         int lm2, ln2, la2;
  312.         int rm2, rn2, ra2;
  313.         int i, j, k;
  314.        
  315.         cm=(s16)(iblk[0]+(iblk[1]<<8));
  316.         cn=(s16)(iblk[2]+(iblk[3]<<8));
  317.         ca=(cm+cn)>>1;
  318.  
  319.         i=((s16)(iblk[4]<<8));
  320.         j=((s16)(iblk[5]<<8));
  321.  
  322.         lm=cm+i; rm=cm-i;
  323.         ln=cn+j; rn=cn-j;
  324.  
  325.         lm=(lm<(-32768))?(-32768):((lm<32768)?lm:32767);
  326.         ln=(ln<(-32768))?(-32768):((ln<32768)?ln:32767);
  327.         rm=(rm<(-32768))?(-32768):((rm<32768)?rm:32767);
  328.         rn=(rn<(-32768))?(-32768):((rn<32768)?rn:32767);
  329.  
  330.         for(i=0; i<128; i++)
  331.         {
  332.                 oblk[i]=ca;
  333.         }
  334.                
  335.         for(i=0; i<16; i++)
  336.         {
  337.                 p0=(iblk[16+(i>>1)]>>((i&1)*4))&15;
  338.                 p1=(iblk[24+(i>>1)]>>((i&1)*4))&15;
  339. //              cm2=tcmb[i];
  340. //              cn2=tcnb[i];
  341.  
  342. //              s0=(cn-cm);
  343. //              s1=(cn-cm);
  344.        
  345.                 s0=(ln-lm);
  346.                 s1=(rn-rm);
  347.                 lm2=((s0*p0+8)>>4)+lm;
  348.                 ln2=((s0*p1+8)>>4)+lm;
  349.                 rm2=((s1*p0+8)>>4)+rm;
  350.                 rn2=((s1*p1+8)>>4)+rm;
  351.  
  352. //              cm2=((s1*p0+8)>>4)+cm;
  353. //              cn2=((s1*p1+8)>>4)+cm;
  354.  
  355.                 lm2=(lm2<lm)?lm:((lm2<ln)?lm2:ln);
  356.                 ln2=(ln2<lm)?lm:((ln2<ln)?ln2:ln);
  357.                 rm2=(rm2<rm)?rm:((rm2<rn)?rm2:rn);
  358.                 rn2=(rn2<rm)?rm:((rn2<rn)?rn2:rn);
  359.  
  360. //              cm2=(cm2<cm)?cm:((cm2<cn)?cm2:cn);
  361. //              cn2=(cn2<cm)?cm:((cn2<cn)?cn2:cn);
  362.        
  363. //              p2=(p0+p1)>>1;
  364. //              if(p2<cm)p2=cm;
  365. //              if(p2>cn)p2=cn;
  366.                
  367.                 for(j=0; j<4; j++)
  368.                 {
  369.                         k=i*4+j;
  370.                
  371. //                      oblk[i*16+j]=p2;
  372.                         p0=(iblk[8+(k>>3)]&(1<<(k&7)));
  373.                         oblk[k*2+0]=p0?ln2:lm2;
  374.                         oblk[k*2+1]=p0?rn2:rm2;
  375.  
  376. //                      oblk[k*2+0]=p0?cn2:cm2;
  377. //                      oblk[k*2+1]=p0?cn2:cm2;
  378.                 }
  379.         }
  380. }
  381.  
  382. BTAC_API void BGBTAC_EncodeStream8StereoS16(s16 *iblk, byte *oblk, int len)
  383. {
  384.         int i, j, n;
  385.        
  386.         n=(len+63)/64;
  387.         for(i=0; i<n; i++)
  388.         {
  389.                 BGBTAC_EncodeBlock8StereoS16(iblk+i*2*64, oblk+i*32);
  390.         }
  391. }
  392.  
  393. BTAC_API void BGBTAC_DecodeStream8StereoS16(byte *iblk, s16 *oblk, int len)
  394. {
  395.         int p0, p1, p2, p3;
  396.         int q0, q1, q2, q3;
  397.         int i, j, n;
  398.        
  399.         n=(len+63)/64;
  400.         for(i=0; i<n; i++)
  401.         {
  402.                 BGBTAC_DecodeBlock8StereoS16(iblk+i*32, oblk+i*2*64);
  403.         }
  404.        
  405.         //deblocking...
  406.         for(i=1; i<(n-1); i++)
  407.                 for(j=0; j<2; j++)
  408.         {
  409. #if 0
  410.                 p0=oblk[i*64*2-2];
  411.                 p1=oblk[i*64*2-1];
  412.                 p2=oblk[i*64*2+0];
  413.                 p3=oblk[i*64*2+1];
  414.  
  415.                 q0=(11*p0+5*p2)>>4;
  416.                 q1=(11*p1+5*p3)>>4;
  417.                 q2=(11*p2+5*p0)>>4;
  418.                 q3=(11*p3+5*p1)>>4;
  419.                
  420.                 oblk[i*64*2-2]=q0;
  421.                 oblk[i*64*2-1]=q1;
  422.                 oblk[i*64*2+0]=q2;
  423.                 oblk[i*64*2+1]=q3;
  424. #endif
  425.  
  426. #if 1
  427.                 p0=oblk[i*64*2-4+j];
  428.                 p1=oblk[i*64*2-2+j];
  429.                 p2=oblk[i*64*2+0+j];
  430.                 p3=oblk[i*64*2+2+j];
  431.  
  432.                 q0=(128*p0+ 64*p1+ 48*p2+ 16*p3)>>8;
  433.                 q1=( 48*p0+128*p1+ 48*p2+ 32*p3)>>8;
  434.                 q2=( 32*p0+ 48*p1+128*p2+ 48*p3)>>8;
  435.                 q3=( 16*p0+ 48*p1+ 64*p2+128*p3)>>8;
  436.                
  437.                 oblk[i*64*2-4+j]=q0;
  438.                 oblk[i*64*2-2+j]=q1;
  439.                 oblk[i*64*2+0+j]=q2;
  440.                 oblk[i*64*2+2+j]=q3;
  441. #endif
  442.         }
  443. }