From e63147a042bebb1cdbeec3b82cc263d16f537a95 Mon Sep 17 00:00:00 2001
From: John Glover <john@john-glovers-macbook.local>
Date: Fri, 17 Dec 2010 17:37:59 +0000
Subject: Separated residual parameters/memory into a new SMS_ResidualParams
 structure

---
 sms/analysis.c | 37 ++++++++++------------
 sms/residual.c |  9 +++---
 sms/sms.c      | 99 +++++++++++++++++++++++++++++++++++++++++++---------------
 sms/sms.h      | 25 +++++++++++++--
 4 files changed, 117 insertions(+), 53 deletions(-)

(limited to 'sms')

diff --git a/sms/analysis.c b/sms/analysis.c
index ec4e0fe..9e22ca3 100644
--- a/sms/analysis.c
+++ b/sms/analysis.c
@@ -334,17 +334,16 @@ int sms_findResidual(int sizeSynthesis, sfloat* pSynthesis,
                      int sizeResidual, sfloat* pResidual,
                      SMS_AnalParams *analParams)
 {
-    if(sizeSynthesis != sizeOriginal || sizeOriginal != sizeResidual)
+    if(sizeResidual < sizeOriginal)
     {
+        sms_error("Residual signal length is smaller than the original signal length");
         return -1;
     }
-
-    /* perform preemphasis */
-    int i;
-    for(i = 0; i < sizeSynthesis; i++)
-    {
-        pOriginal[i] = sms_preEmphasis(pOriginal[i], analParams);
-    }
+    /*if(sizeSynthesis > sizeOriginal)*/
+    /*{*/
+    /*    printf("Warning: synthesised signal is longer than the orignal signal. ");*/
+    /*    printf("Orignal will be zero padded.\n");*/
+    /*}*/
 
     /*sms_residual(sizeResidual, pSynthesis, pOriginal, pResidual);*/
     return 0;
@@ -536,47 +535,45 @@ int sms_analyze(int sizeWaveform, sfloat *pWaveform, SMS_Data *pSmsData, SMS_Ana
         if(pAnalParams->ppFrames[0]->iStatus != SMS_FRAME_EMPTY &&
            pAnalParams->ppFrames[0]->iStatus != SMS_FRAME_END)
         {
-            int sizeResidual = pAnalParams->sizeHop * 2;
             int iSoundLoc = pAnalParams->ppFrames[0]->iFrameSample - pAnalParams->sizeHop;
             sfloat *pOriginal = &(pAnalParams->soundBuffer.pFBuffer[iSoundLoc -
                                   pAnalParams->soundBuffer.iMarker]);
 
             int sizeData = MIN(pAnalParams->soundBuffer.sizeBuffer -
                                (iSoundLoc - pAnalParams->soundBuffer.iMarker),
-                               pAnalParams->sizeResidual);
-
-            if(sizeData > pAnalParams->sizeResidual)
+                               pAnalParams->residualParams.residualSize);
+            if(sizeData > pAnalParams->residualParams.residualSize)
             {
                 sms_error("Residual size larger than expected.");
                 return -1;
             }
-            else if(sizeData < pAnalParams->sizeResidual)
+            else if(sizeData < pAnalParams->residualParams.residualSize)
             {
                 /* should only happen if we're at the end of a sound, unless hop size changes */
-                sms_getWindow(sizeData, pAnalParams->residualWindow, SMS_WIN_HAMMING);
-                sms_scaleWindow(sizeData, pAnalParams->residualWindow);
+                sms_getWindow(sizeData, pAnalParams->residualParams.residualWindow, SMS_WIN_HAMMING);
+                sms_scaleWindow(sizeData, pAnalParams->residualParams.residualWindow);
             }
 
             /* obtain residual sound from original and synthesized sounds.  accumulate the residual percentage.*/
             pAnalParams->fResidualAccumPerc += sms_residual(sizeData,
                                                             pAnalParams->synthBuffer.pFBuffer,
                                                             pOriginal,
-                                                            pAnalParams->residual,
-                                                            pAnalParams->residualWindow);
+                                                            pAnalParams->residualParams.residual,
+                                                            pAnalParams->residualParams.residualWindow);
 
             if(pAnalParams->iStochasticType == SMS_STOC_APPROX)
             {
                 /* filter residual with a high pass filter (it solves some problems) */
-                sms_filterHighPass(sizeData, pAnalParams->residual, pAnalParams->iSamplingRate);
+                sms_filterHighPass(sizeData, pAnalParams->residualParams.residual, pAnalParams->iSamplingRate);
 
                 /* approximate residual */
-                sms_stocAnalysis(sizeData, pAnalParams->residual, pAnalParams->residualWindow, 
+                sms_stocAnalysis(sizeData, pAnalParams->residualParams.residual, pAnalParams->residualParams.residualWindow, 
                                  pSmsData, pAnalParams);
             }
             else if(pAnalParams->iStochasticType == SMS_STOC_IFFT)
             {
                 int sizeMag = sms_power2(sizeData >> 1);
-                sms_spectrum(sizeData, pAnalParams->residual, pAnalParams->residualWindow, 
+                sms_spectrum(sizeData, pAnalParams->residualParams.residual, pAnalParams->residualParams.residualWindow, 
                              sizeMag, pSmsData->pFStocCoeff, pSmsData->pResPhase,
                              pAnalParams->fftBuffer);
             }
diff --git a/sms/residual.c b/sms/residual.c
index b69a28f..ae9bf9a 100644
--- a/sms/residual.c
+++ b/sms/residual.c
@@ -26,13 +26,12 @@
 
 /*! \brief get the residual waveform
  *
- * \param sizeWindow       size of buffers
- * \param pSynthesis       pointer to deterministic component
- * \param pOriginal          pointer to original waveform
- * \param pResidual        pointer to output residual waveform
+ * \param sizeWindow size of buffers
+ * \param pSynthesis pointer to deterministic component
+ * \param pOriginal  pointer to original waveform
+ * \param pResidual  pointer to output residual waveform
  * \param pWindow    pointer to windowing array
  * \return residual percentage (0 if residual was not large enough)
- \todo why is residual energy percentage computed this way? should be optional and in a seperate function
  */
 int sms_residual(int sizeWindow, sfloat *pSynthesis, sfloat *pOriginal, sfloat *pResidual, sfloat *pWindow)
 {
diff --git a/sms/sms.c b/sms/sms.c
index 8294224..825aca1 100644
--- a/sms/sms.c
+++ b/sms/sms.c
@@ -162,9 +162,10 @@ void sms_initAnalParams(SMS_AnalParams *pAnalParams)
     pAnalParams->pFrames = NULL;
     pAnalParams->ppFrames = NULL;
     /* residual */
-    pAnalParams->sizeResidual = pAnalParams->sizeHop * 2;
-    pAnalParams->residual = NULL;
-    pAnalParams->residualWindow = NULL;
+    sms_initResidualParams(&pAnalParams->residualParams);
+    /*pAnalParams->sizeResidual = pAnalParams->sizeHop * 2;*/
+    /*pAnalParams->residual = NULL;*/
+    /*pAnalParams->residualWindow = NULL;*/
     /* peak continuation */
     pAnalParams->guideStates = NULL;
     pAnalParams->guides = NULL;
@@ -321,21 +322,8 @@ int sms_initAnalysis(SMS_AnalParams *pAnalParams)
     }
 
     /* memory for residual */
-    pAnalParams->sizeResidual = pAnalParams->sizeHop * 2;
-    pAnalParams->residual = (sfloat *)calloc(pAnalParams->sizeResidual, sizeof(sfloat));
-    if(pAnalParams->residual == NULL)
-    {
-        sms_error("Could not allocate memory for residual");
-        return -1;
-    }
-    pAnalParams->residualWindow = (sfloat *)calloc(pAnalParams->sizeResidual, sizeof(sfloat));
-    if(pAnalParams->residualWindow == NULL)
-    {
-        sms_error("Could not allocate memory for residualWindow");
-        return -1;
-    }
-    sms_getWindow(pAnalParams->sizeResidual, pAnalParams->residualWindow, SMS_WIN_HAMMING);
-    sms_scaleWindow(pAnalParams->sizeResidual, pAnalParams->residualWindow);
+    pAnalParams->residualParams.residualSize = pAnalParams->sizeHop * 2;
+    sms_initResidual(&pAnalParams->residualParams);
 
     /* memory for guide states */
     pAnalParams->guideStates = (int *)calloc(pAnalParams->nGuides, sizeof(int));
@@ -370,7 +358,7 @@ int sms_initAnalysis(SMS_AnalParams *pAnalParams)
     }
 
     /* stochastic analysis */
-    pAnalParams->sizeStocMagSpectrum = sms_power2(pAnalParams->sizeResidual) >> 1;
+    pAnalParams->sizeStocMagSpectrum = sms_power2(pAnalParams->residualParams.residualSize) >> 1;
     pAnalParams->stocMagSpectrum = (sfloat *)calloc(pAnalParams->sizeStocMagSpectrum, sizeof(sfloat));
     if(pAnalParams->stocMagSpectrum == NULL)
     {
@@ -475,6 +463,71 @@ int sms_initSynth(SMS_SynthParams *pSynthParams)
     return SMS_OK;
 }
 
+/*! \brief give default values to an SMS_ResidualParams struct 
+ * 
+ * \param residualParams pointer to residual data structure
+ */
+void sms_initResidualParams(SMS_ResidualParams *residualParams)
+{
+    residualParams->residualSize = 0;
+    residualParams->residual = NULL;
+    residualParams->residualWindow = NULL;
+    residualParams->residualMag = 0.0;
+    residualParams->originalMag = 0.0;
+}
+
+/*! \brief initialize residual data structure
+ * 
+ * \param residualParams pointer to synthesis paramaters
+ * \return 0 on success, -1 on error
+ */
+int sms_initResidual(SMS_ResidualParams *residualParams)
+{
+    if(residualParams->residualSize <= 0)
+    {
+        sms_error("Residual size must be a positive integer");
+        return -1;
+    }
+
+    /* */
+    residualParams->residual = (sfloat *)calloc(residualParams->residualSize, sizeof(sfloat));
+    if(residualParams->residual == NULL)
+    {
+        sms_error("Could not allocate memory for residual");
+        return -1;
+    }
+
+    /* */
+    residualParams->residualWindow = (sfloat *)calloc(residualParams->residualSize, sizeof(sfloat));
+    if(residualParams->residualWindow == NULL)
+    {
+        sms_error("Could not allocate memory for residualWindow");
+        return -1;
+    }
+    sms_getWindow(residualParams->residualSize, residualParams->residualWindow, SMS_WIN_HAMMING);
+    sms_scaleWindow(residualParams->residualSize, residualParams->residualWindow);
+
+    return 0;
+}
+
+/*! \brief free residual data
+ * 
+ * frees all the memory allocated to an SMS_ResidualParams by
+ * sms_initResidual
+ *
+ * \param residualParams pointer to residual data structure
+ */
+void sms_freeResidual(SMS_ResidualParams *residualParams)
+{
+    if(residualParams->residual)
+        free(residualParams->residual);
+    if(residualParams->residualWindow)
+        free(residualParams->residualWindow);
+
+    residualParams->residual = NULL;
+    residualParams->residualWindow = NULL;
+}
+
 /*! \brief free analysis data
  * 
  * frees all the memory allocated to an SMS_AnalParams by
@@ -502,16 +555,14 @@ void sms_freeAnalysis(SMS_AnalParams *pAnalParams)
     }
 
     sms_freeFrame(&pAnalParams->prevFrame);
+    sms_freeResidual(&pAnalParams->residualParams);
+
     if(pAnalParams->soundBuffer.pFBuffer)
         free(pAnalParams->soundBuffer.pFBuffer);
     if((pAnalParams->synthBuffer).pFBuffer)
         free((pAnalParams->synthBuffer).pFBuffer);
     if(pAnalParams->ppFrames)
         free(pAnalParams->ppFrames);
-    if(pAnalParams->residual)
-        free(pAnalParams->residual);
-    if(pAnalParams->residualWindow)
-        free(pAnalParams->residualWindow);
     if(pAnalParams->guideStates)
         free(pAnalParams->guideStates);
     if(pAnalParams->guides)
@@ -525,8 +576,6 @@ void sms_freeAnalysis(SMS_AnalParams *pAnalParams)
     pAnalParams->ppFrames = NULL;
     pAnalParams->soundBuffer.pFBuffer = NULL;
     pAnalParams->synthBuffer.pFBuffer = NULL;
-    pAnalParams->residual = NULL;
-    pAnalParams->residualWindow = NULL;
     pAnalParams->guideStates = NULL;
     pAnalParams->guides = NULL;
     pAnalParams->stocMagSpectrum = NULL;
diff --git a/sms/sms.h b/sms/sms.h
index f998145..e3ac14b 100644
--- a/sms/sms.h
+++ b/sms/sms.h
@@ -187,6 +187,21 @@ typedef struct
     int iPeakChosen; /*!< peak number chosen by the guide */
 } SMS_Guide;
 
+/*! \struct SMS_ResidualParams
+ * \brief structure with information for residual functions
+ *
+ * This structure contains all the necessary settings and memory for residual synthesis.
+ *
+ */
+typedef struct
+{
+    int residualSize;
+    sfloat *residual;
+    sfloat *residualWindow;
+    sfloat residualMag;
+    sfloat originalMag;
+} SMS_ResidualParams;
+
 /*! \struct SMS_AnalParams
  * \brief structure with useful information for analysis functions
  *
@@ -253,9 +268,10 @@ typedef struct
     sfloat phaseSpectrum[SMS_MAX_SPEC];
     sfloat spectrumWindow[SMS_MAX_SPEC];
     sfloat fftBuffer[SMS_MAX_SPEC * 2];
-    int sizeResidual;
-    sfloat *residual;
-    sfloat *residualWindow;
+    SMS_ResidualParams residualParams;
+    //int sizeResidual;
+    //sfloat *residual;
+    //sfloat *residualWindow;
     int *guideStates;
     SMS_Guide* guides;
     sfloat inputBuffer[SMS_MAX_FRAME_SIZE];
@@ -655,6 +671,9 @@ void sms_clearFrame(SMS_Data *pSmsFrame);
 void sms_copyFrame(SMS_Data *pCopySmsFrame, SMS_Data *pOriginalSmsFrame);
 int sms_frameSizeB(SMS_Header *pSmsHeader);
 
+void sms_initResidualParams(SMS_ResidualParams *residualParams);
+int sms_initResidual(SMS_ResidualParams *residualParams);
+void sms_freeResidual(SMS_ResidualParams *residualParams);
 int sms_residual(int sizeWindow, sfloat *pSynthesis, sfloat *pOriginal, 
                  sfloat *pResidual, sfloat *pWindow);
 void sms_filterHighPass(int sizeResidual, sfloat *pResidual, int iSamplingRate);
-- 
cgit v1.2.3