Переглянути джерело

cmProc2.h/c : Added spectral input/output files to cmSpecDist().

Added phase modulation via _smSpecDistPhaseMod() to cmSpecDist().
Changed track score calculation in FrqTrk.
Added attenuation delay state to FrqTrk attenution stage.
master
Kevin Larke 9 роки тому
джерело
коміт
dfc94439da
2 змінених файлів з 124 додано та 27 видалено
  1. 109
    26
      cmProc2.c
  2. 15
    1
      cmProc2.h

+ 109
- 26
cmProc2.c Переглянути файл

@@ -4779,6 +4779,7 @@ cmRC_t    cmFrqTrkInit( cmFrqTrk* p, const cmFrqTrkArgs_t* a )
4779 4779
   p->minTrkN   = a->minTrkSec * a->srate / a->hopSmpCnt;
4780 4780
   p->nextTrkId = 1;
4781 4781
   p->aV        = cmMemResizeZ(cmReal_t,p->aV,p->a.binCnt);
4782
+  p->attenDlyPhsMax = cmMax(3,a->attenDlySec * a->srate / a->hopSmpCnt );
4782 4783
   p->attenPhsMax    = cmMax(3,a->attenAtkSec * a->srate / a->hopSmpCnt );
4783 4784
   
4784 4785
   if( a->logFn != NULL )
@@ -5019,7 +5020,11 @@ void _cmFrqTrkScoreChs( cmFrqTrk* p )
5019 5020
       c->hz_mean = cmVOR_Mean(c->hzV,n);
5020 5021
       c->hz_std  = sqrt(cmVOR_Variance( c->hzV,n,&c->hz_mean));
5021 5022
 
5022
-      c->score = c->db / ((cmMin(0.1,c->db_std) + cmMin(0.1,c->hz_std))/2);
5023
+      //c->score = c->db / ((cmMax(0.1,c->db_std) + cmMax(0.1,c->hz_std))/2);
5024
+
5025
+      c->score = c->db - (c->db_std * 5) - (c->hz_std/50);
5026
+
5027
+      //printf("%f %f %f %f %f\n",c->db,cmMin(0.1,c->db_std),c->hz,cmMin(0.1,c->hz_std),c->score);
5023 5028
     }
5024 5029
 }
5025 5030
 
@@ -5082,8 +5087,9 @@ void _cmFrqTrkUpdateFilter( cmFrqTrk* p )
5082 5087
       // 
5083 5088
       if( c->score >= p->a.attenThresh && c->state == kNoStateFrqTrkId )
5084 5089
       {
5090
+        //printf("%f\n",c->score);
5085 5091
         c->attenPhsIdx = 0;
5086
-        c->state  = kAtkFrqTrkId;        
5092
+        c->state       = kDlyFrqTrkId;        
5087 5093
       }
5088 5094
 
5089 5095
       switch( c->state )
@@ -5091,8 +5097,16 @@ void _cmFrqTrkUpdateFilter( cmFrqTrk* p )
5091 5097
         case kNoStateFrqTrkId:
5092 5098
           break;
5093 5099
 
5100
+        case kDlyFrqTrkId:
5101
+          c->attenPhsIdx += 1;
5102
+
5103
+          if( c->attenPhsIdx >= p->attenDlyPhsMax && c->dN == 0 )
5104
+            c->state = kAtkFrqTrkId;          
5105
+
5106
+          break;
5107
+
5094 5108
         case kAtkFrqTrkId:
5095
-          if( c->attenPhsIdx < p->attenPhsMax )
5109
+          if( c->attenPhsIdx < p->attenDlyPhsMax + p->attenPhsMax )
5096 5110
           {
5097 5111
 
5098 5112
             c->attenGain = cmMin(1.0,p->a.attenGain * c->attenPhsIdx / p->attenPhsMax);
@@ -5101,7 +5115,7 @@ void _cmFrqTrkUpdateFilter( cmFrqTrk* p )
5101 5115
           }
5102 5116
 
5103 5117
           c->attenPhsIdx += 1;
5104
-          if( c->attenPhsIdx >= p->attenPhsMax )
5118
+          if( c->attenPhsIdx >= p->attenDlyPhsMax + p->attenPhsMax )
5105 5119
             c->state = kSusFrqTrkId;
5106 5120
           break;
5107 5121
 
@@ -5275,7 +5289,7 @@ void _cmFrqTrkNewChs( cmFrqTrk* p, const cmReal_t* dbV, const cmReal_t* hzV, uns
5275 5289
 
5276 5290
 void _cmFrqTrkApplyFrqBias( cmFrqTrk* p, cmReal_t* xV )
5277 5291
 {
5278
-  // 1+2*([0:.01:1].^4)
5292
+  // convert to decibel scale (0.0 - 100.0) and then scale to (0.0 to 1.0)
5279 5293
   unsigned i;
5280 5294
   for(i=0; i<p->bN; ++i)
5281 5295
     xV[i] =  cmMax(0.0, (20*log10( cmMax(xV[i]/1.5,0.00001)) + 100.0)/100.0);
@@ -5318,20 +5332,20 @@ cmRC_t cmFrqTrkExec( cmFrqTrk* p, const cmReal_t* magV, const cmReal_t* phsV, co
5318 5332
   // copy p->dbV to dbM[hi,:] 
5319 5333
   cmVOR_CopyN(p->dbM + p->hi, p->bN, p->hN, p->dbV, 1 );
5320 5334
 
5321
-  // increment hi
5335
+  // increment hi to next column to fill in dbM[]
5322 5336
   p->hi = (p->hi + 1) % p->hN;
5323 5337
 
5324
-  // Form the spectral magnitude profile by taking the mean over time
5325
-  // of the last hN magnitude vectors
5338
+  // Set dbV[] to spectral magnitude profile by taking the mean over time
5339
+  // of the last hN magnitude vectors 
5326 5340
   cmVOR_MeanM2(p->dbV, p->dbM, p->hN, p->bN, 0, cmMin(p->fN+1,p->hN));
5327 5341
   //cmVOR_MeanM(p->dbV, p->dbM, p->hN, p->bN, 0);
5328 5342
 
5329 5343
   if( p->fN >= p->hN )
5330 5344
   {
5331
-    // set the indexes of the peaks above pkThreshDb in i0[]
5345
+    // set pkiV[] to the indexes of the peaks above pkThreshDb in i0[]
5332 5346
     unsigned pkN = cmVOR_PeakIndexes(p->pkiV, p->bN, p->dbV, p->bN, p->a.pkThreshDb );
5333 5347
 
5334
-    // generate the peak frequencies from the magnitude
5348
+    // set hzV[] to the peak frequencies assoc'd with peaks at dbV[ pkiV[] ].
5335 5349
     _cmFrqTrkMagnToHz(p, p->dbV, p->pkiV, pkN, hzV );
5336 5350
 
5337 5351
     // extend the existing trackers
@@ -5485,6 +5499,7 @@ cmSpecDist_t* cmSpecDistAlloc( cmCtx* ctx,cmSpecDist_t* ap, unsigned procSmpCnt,
5485 5499
 {
5486 5500
   cmSpecDist_t* p = cmObjAlloc( cmSpecDist_t, ctx, ap );
5487 5501
 
5502
+  p->iSpecVa   = cmVectArrayAlloc(ctx,kRealVaFl);
5488 5503
   p->oSpecVa   = cmVectArrayAlloc(ctx,kRealVaFl);
5489 5504
 
5490 5505
   if( procSmpCnt != 0 )
@@ -5505,8 +5520,13 @@ cmRC_t cmSpecDistFree( cmSpecDist_t** pp )
5505 5520
   cmSpecDist_t* p = *pp;
5506 5521
   
5507 5522
   cmSpecDistFinal(p);
5523
+  cmVectArrayFree(&p->iSpecVa);
5508 5524
   cmVectArrayFree(&p->oSpecVa);
5509 5525
   cmMemPtrFree(&p->hzV);
5526
+  cmMemPtrFree(&p->iSpecM);
5527
+  cmMemPtrFree(&p->oSpecM);
5528
+  cmMemPtrFree(&p->iSpecV);
5529
+  cmMemPtrFree(&p->oSpecV);
5510 5530
   cmObjFree(pp);
5511 5531
   return cmOkRC;
5512 5532
 
@@ -5523,6 +5543,7 @@ cmRC_t cmSpecDistInit( cmSpecDist_t* p, unsigned procSmpCnt, double srate, unsig
5523 5543
   unsigned flags = 0;
5524 5544
 
5525 5545
 
5546
+  p->srate        = srate;
5526 5547
   p->wndSmpCnt    = wndSmpCnt;
5527 5548
   p->hopSmpCnt    = (unsigned)floor(wndSmpCnt/hopFcmt);
5528 5549
   p->procSmpCnt   = procSmpCnt;
@@ -5550,9 +5571,10 @@ cmRC_t cmSpecDistInit( cmSpecDist_t* p, unsigned procSmpCnt, double srate, unsig
5550 5571
   fta.pkMaxHz       = 20000;
5551 5572
   fta.whFiltCoeff   = 0.33;
5552 5573
 
5553
-  fta.attenThresh = 900.0;
5554
-  fta.attenGain   = 1.0; 
5555
-  fta.attenAtkSec = 0.25;  
5574
+  fta.attenThresh = 0.4;
5575
+  fta.attenGain   = 0.5; 
5576
+  fta.attenDlySec = 1.0;
5577
+  fta.attenAtkSec = 1.0;  
5556 5578
 
5557 5579
   fta.logFn         = "/home/kevin/temp/frqtrk/trk_log.va";
5558 5580
   fta.levelFn       = "/home/kevin/temp/frqtrk/level.va";
@@ -5587,6 +5609,15 @@ cmRC_t cmSpecDistInit( cmSpecDist_t* p, unsigned procSmpCnt, double srate, unsig
5587 5609
   p->aeMin  = 1000;
5588 5610
   p->aeMax  = -1000;
5589 5611
 
5612
+  
5613
+  double histSecs = 0.05;
5614
+  p->hN      = cmMax(1,histSecs * p->srate / p->hopSmpCnt );
5615
+  p->iSpecM  = cmMemResizeZ(cmReal_t,p->iSpecM,p->hN*p->pva->binCnt);
5616
+  p->oSpecM  = cmMemResizeZ(cmReal_t,p->oSpecM,p->hN*p->pva->binCnt);
5617
+  p->iSpecV  = cmMemResizeZ(cmReal_t,p->iSpecV,      p->pva->binCnt);
5618
+  p->oSpecV  = cmMemResizeZ(cmReal_t,p->oSpecV,      p->pva->binCnt);
5619
+  p->hi      = 0;
5620
+
5590 5621
 
5591 5622
   //p->bypOut = cmMemResizeZ(cmSample_t, p->bypOut, procSmpCnt );
5592 5623
 
@@ -5597,6 +5628,7 @@ cmRC_t cmSpecDistFinal(cmSpecDist_t* p )
5597 5628
 {
5598 5629
   cmRC_t rc = cmOkRC;
5599 5630
 
5631
+  cmVectArrayWrite(p->iSpecVa, "/home/kevin/temp/frqtrk/iSpec.va");
5600 5632
   cmVectArrayWrite(p->oSpecVa, "/home/kevin/temp/frqtrk/oSpec.va");
5601 5633
 
5602 5634
   cmPvAnlFree(&p->pva);
@@ -5777,27 +5809,58 @@ void _cmSpecDistAmpEnvMode( cmSpecDist_t* p, cmReal_t* X1m )
5777 5809
 
5778 5810
 }
5779 5811
 
5812
+void _cmSpecDistPhaseMod( cmSpecDist_t* p, cmReal_t* phsV, unsigned binCnt )
5813
+{
5814
+  unsigned i;
5815
+  cmReal_t offs =  sin( 0.1 * 2.0 * M_PI * (p->phaseModIndex++) / (p->srate/p->hopSmpCnt) );
5816
+
5817
+  //printf("offs %f %i %i %f\n",offs,p->phaseModIndex,p->hopSmpCnt,p->srate);
5818
+
5819
+  cmReal_t new_phs = phsV[0] + offs;
5820
+  for(i=0; i<binCnt-1; ++i)
5821
+  {
5822
+    while( new_phs > M_PI )
5823
+      new_phs -= 2.0*M_PI;
5824
+
5825
+    while( new_phs < -M_PI )
5826
+      new_phs += 2.0*M_PI;
5827
+
5828
+    cmReal_t d = phsV[i+1] - phsV[i];
5829
+
5830
+    phsV[i] = new_phs;
5831
+
5832
+    new_phs += d;    
5833
+  }
5834
+  
5835
+}
5836
+
5780 5837
 cmRC_t  cmSpecDistExec( cmSpecDist_t* p, const cmSample_t* sp, unsigned sn )
5781 5838
 {
5782 5839
 
5783 5840
   assert( sn == p->procSmpCnt );
5784 5841
 
5842
+  bool recordFl = false;
5843
+
5785 5844
   // cmPvAnlExec() returns true when it calc's a new spectral output frame
5786 5845
   if( cmPvAnlExec( p->pva, sp, sn ) )
5787 5846
   {
5788 5847
     cmReal_t X1m[p->pva->binCnt]; 
5789 5848
 
5849
+    // take the mean of the the input magntitude spectrum
5790 5850
     cmReal_t u0 = cmVOR_Mean(p->pva->magV,p->pva->binCnt);
5791 5851
 
5792
-    //cmFrqTrkExec(p->ft, p->pva->magV, p->pva->phsV, NULL );
5793
-
5794
-    // apply the freq track suppression filter
5795
-    //cmVOR_MultVVV(X1m, p->pva->binCnt,p->pva->magV, p->ft->aV );
5852
+    if(recordFl)
5853
+    {
5854
+      // store a time windowed average of the input spectrum to p->iSpecV
5855
+      cmVOR_CopyN(p->iSpecM + p->hi, p->pva->binCnt, p->hN, X1m, 1 );
5856
+      cmVOR_MeanM2(p->iSpecV, p->iSpecM, p->hN, p->pva->binCnt, 0, cmMin(p->fi+1,p->hN));
5857
+    }
5796 5858
 
5797 5859
     cmVOR_AmplToDbVV(X1m, p->pva->binCnt, p->pva->magV, -1000.0 );
5798 5860
     //cmVOR_AmplToDbVV(X1m, p->pva->binCnt, X1m, -1000.0 );
5799 5861
 
5800 5862
 
5863
+
5801 5864
     switch( p->mode )
5802 5865
     {
5803 5866
       case kBypassModeSdId:
@@ -5838,22 +5901,25 @@ cmRC_t  cmSpecDistExec( cmSpecDist_t* p, const cmSample_t* sp, unsigned sn )
5838 5901
         break;
5839 5902
     }
5840 5903
 
5841
-    //cmVectArrayAppendR(p->oSpecVa,X1m,p->pva->binCnt);
5842
-    
5843 5904
     cmVOR_DbToAmplVV(X1m, p->pva->binCnt, X1m );
5844 5905
 
5845 5906
 
5846 5907
     // run and apply the tracker/supressor
5847
-    cmFrqTrkExec(p->ft, X1m, p->pva->phsV, NULL );
5848
-    cmVOR_MultVV(X1m, p->pva->binCnt,p->ft->aV );
5908
+    cmFrqTrkExec(p->ft, X1m, p->pva->phsV, NULL ); 
5909
+    //cmVOR_MultVV(X1m, p->pva->binCnt,p->ft->aV );
5849 5910
 
5850 5911
 
5912
+    // convert the mean input magnitude to db
5851 5913
     cmReal_t idb = 20*log10(u0);
5914
+    
5915
+    // get the mean output magnitude spectra
5852 5916
     cmReal_t u1 = cmVOR_Mean(X1m,p->pva->binCnt);
5853 5917
 
5854 5918
     if( idb > -150.0 )
5855 5919
     {
5856
-      p->ogain = u0/u1;
5920
+      // set the output gain such that the mean output magnitude
5921
+      // will match the mean input magnitude
5922
+      p->ogain = u0/u1;  
5857 5923
     }
5858 5924
     else
5859 5925
     {
@@ -5861,17 +5927,34 @@ cmRC_t  cmSpecDistExec( cmSpecDist_t* p, const cmSample_t* sp, unsigned sn )
5861 5927
       p->ogain *= a0;
5862 5928
     }
5863 5929
 
5864
-    //cmReal_t v[] = { u0, u1, idb, 20*log10(u1), p->ogain };
5865
-    //unsigned vn = sizeof(v)/sizeof(v[0]);
5866
-    //cmVectArrayAppendR(p->oSpecVa,v,vn);
5867
-
5868 5930
     cmVOR_MultVS(X1m,p->pva->binCnt,cmMin(4.0,p->ogain));
5869 5931
 
5870 5932
 
5871 5933
     //cmFbCtlExec(p->fbc,X1m);
5872 5934
 
5935
+    //cmReal_t v[ p->pva->binCnt ];
5936
+    //cmVOR_Copy(v,p->pva->binCnt,p->pva->phsV);
5937
+    //_cmSpecDistPhaseMod(p, v, p->pva->binCnt );
5938
+
5939
+    
5940
+    if(recordFl)
5941
+    {
5942
+
5943
+      // store a time windowed average of the output spectrum to p->iSpecV
5944
+      cmVOR_CopyN(p->oSpecM + p->hi, p->pva->binCnt, p->hN, X1m, 1 );
5945
+      cmVOR_MeanM2(p->oSpecV, p->oSpecM, p->hN, p->pva->binCnt, 0, cmMin(p->fi+1,p->hN));
5946
+      
5947
+      // store iSpecV and oSpecV to iSpecVa and oSpecVa to create debugging files
5948
+      cmVectArrayAppendR(p->iSpecVa,p->iSpecV,p->pva->binCnt);
5949
+      cmVectArrayAppendR(p->oSpecVa,p->oSpecV,p->pva->binCnt);
5950
+
5951
+      p->hi = (p->hi + 1) % p->hN;
5952
+    }
5953
+    
5954
+
5873 5955
     cmPvSynExec(p->pvs, X1m, p->pva->phsV );
5874 5956
   
5957
+    p->fi += 1;
5875 5958
   }
5876 5959
  
5877 5960
   return cmOkRC;

+ 15
- 1
cmProc2.h Переглянути файл

@@ -902,6 +902,7 @@ extern "C" {
902 902
   typedef enum
903 903
   {
904 904
     kNoStateFrqTrkId,
905
+    kDlyFrqTrkId,
905 906
     kAtkFrqTrkId,
906 907
     kSusFrqTrkId,
907 908
     kDcyFrqTrkId
@@ -924,6 +925,7 @@ extern "C" {
924 925
 
925 926
     cmReal_t    attenThresh;
926 927
     cmReal_t    attenGain; 
928
+    cmReal_t    attenDlySec;
927 929
     cmReal_t    attenAtkSec;   
928 930
 
929 931
     const char* logFn;          // log file name or NULL if no file is to be written
@@ -985,6 +987,7 @@ extern "C" {
985 987
     unsigned      deadTrkCnt;
986 988
 
987 989
     cmReal_t*     aV;
990
+    int           attenDlyPhsMax;
988 991
     int           attenPhsMax;
989 992
 
990 993
     cmWhFilt*      wf;
@@ -1106,9 +1109,20 @@ extern "C" {
1106 1109
     cmReal_t  aeMax;
1107 1110
     cmReal_t  aeUnit;
1108 1111
 
1109
-    cmVectArray_t* oSpecVa;
1110 1112
     cmReal_t ogain;
1111 1113
 
1114
+    unsigned phaseModIndex;
1115
+
1116
+    unsigned       fi;          // total count of frames processed by cmSpecDistExec()
1117
+    unsigned       hN;
1118
+    unsigned       hi;
1119
+    cmReal_t*      iSpecM;      // iSpecMtx[hN binN]
1120
+    cmReal_t*      iSpecV;      // mean of rows of iSpecM 
1121
+    cmVectArray_t* iSpecVa;     
1122
+    cmReal_t*      oSpecM;      // oSpecMtx[hN binN]
1123
+    cmReal_t*      oSpecV;      // mean of rows of oSpecM
1124
+    cmVectArray_t* oSpecVa;
1125
+
1112 1126
   } cmSpecDist_t;
1113 1127
 
1114 1128
   cmSpecDist_t*     cmSpecDistAlloc( cmCtx* ctx,cmSpecDist_t* ap, unsigned procSmpCnt, double srate, unsigned wndSmpCnt, unsigned hopFcmt, unsigned olaWndTypeId  ); 

Завантаження…
Відмінити
Зберегти