decoder excitation now in 16-bit precision (was 32), which saves quite a bit
[speexdsp.git] / src / speexdec.c
index c011eb4..2a3876a 100644 (file)
@@ -1,4 +1,4 @@
-/* Copyright (C) 2002-2003 Jean-Marc Valin 
+/* Copyright (C) 2002-2006 Jean-Marc Valin 
    File: speexdec.c
 
    Redistribution and use in source and binary forms, with or without
    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */
 
+#ifdef HAVE_CONFIG_H
+# include "config.h"
+#endif
+
 #include <stdio.h>
 #if !defined WIN32 && !defined _WIN32
 #include <unistd.h>
@@ -80,7 +84,7 @@
 #include <speex/speex_header.h>
 #include <speex/speex_stereo.h>
 #include <speex/speex_callbacks.h>
-#include "misc.h"
+#include "wav_io.h"
 
 #define MAX_FRAME_SIZE 2000
 
@@ -286,13 +290,13 @@ void usage()
 void version()
 {
    printf ("speexdec (Speex decoder) version " SPEEX_VERSION " (compiled " __DATE__ ")\n");
-   printf ("Copyright (C) 2002-2003 Jean-Marc Valin\n");
+   printf ("Copyright (C) 2002-2006 Jean-Marc Valin\n");
 }
 
 void version_short()
 {
    printf ("speexdec version " SPEEX_VERSION "\n");
-   printf ("Copyright (C) 2002-2003 Jean-Marc Valin\n");
+   printf ("Copyright (C) 2002-2006 Jean-Marc Valin\n");
 }
 
 static void *process_header(ogg_packet *op, int enh_enabled, int *frame_size, int *rate, int *nframes, int forceMode, int *channels, SpeexStereoState *stereo, int *extra_headers, int quiet)
@@ -309,7 +313,7 @@ static void *process_header(ogg_packet *op, int enh_enabled, int *frame_size, in
       fprintf (stderr, "Cannot read header\n");
       return NULL;
    }
-   if (header->mode >= SPEEX_NB_MODES)
+   if (header->mode >= SPEEX_NB_MODES || header->mode<0)
    {
       fprintf (stderr, "Mode number %d does not (yet/any longer) exist in this version\n", 
                header->mode);
@@ -319,7 +323,8 @@ static void *process_header(ogg_packet *op, int enh_enabled, int *frame_size, in
    modeID = header->mode;
    if (forceMode!=-1)
       modeID = forceMode;
-   mode = speex_mode_list[modeID];
+
+   mode = speex_lib_get_mode (modeID);
    
    if (header->speex_version_id > 1)
    {
@@ -448,6 +453,7 @@ int main(int argc, char **argv)
    int rate=0;
    int extra_headers;
    int wav_format=0;
+   int lookahead;
 
    enh_enabled = 1;
 
@@ -544,7 +550,7 @@ int main(int argc, char **argv)
       outFile = "";
    wav_format = strlen(outFile)>=4 && (
                                        strcmp(outFile+strlen(outFile)-4,".wav")==0
-                                       || strcmp(inFile+strlen(inFile)-4,".WAV")==0);
+                                       || strcmp(outFile+strlen(outFile)-4,".WAV")==0);
    /*Open input file*/
    if (strcmp(inFile, "-")==0)
    {
@@ -594,6 +600,7 @@ int main(int argc, char **argv)
          page_nb_packets = ogg_page_packets(&og);
          if (page_granule>0 && frame_size)
          {
+            /* FIXME: shift the granule values if --force-* is specified */
             skip_samples = page_nb_packets*frame_size*nframes - (page_granule-last_granule);
             if (ogg_page_eos(&og))
                skip_samples = -skip_samples;
@@ -613,6 +620,7 @@ int main(int argc, char **argv)
             if (packet_count==0)
             {
                st = process_header(&op, enh_enabled, &frame_size, &rate, &nframes, forceMode, &channels, &stereo, &extra_headers, quiet);
+               speex_decoder_ctl(st, SPEEX_GET_LOOKAHEAD, &lookahead);
                if (!nframes)
                   nframes=1;
                if (!st)
@@ -627,8 +635,8 @@ int main(int argc, char **argv)
             {
                /* Ignore extra headers */
             } else {
-               packet_no++;
                int lost=0;
+               packet_no++;
                if (loss_percent>0 && 100*((float)rand())/RAND_MAX<loss_percent)
                   lost=1;
 
@@ -685,15 +693,16 @@ int main(int argc, char **argv)
                      int frame_offset = 0;
                      int new_frame_size = frame_size;
                      /*printf ("packet %d %d\n", packet_no, skip_samples);*/
+                     /*fprintf (stderr, "packet %d %d %d\n", packet_no, skip_samples, lookahead);*/
                      if (packet_no == 1 && j==0 && skip_samples > 0)
                      {
                         /*printf ("chopping first packet\n");*/
-                        new_frame_size -= skip_samples;
-                        frame_offset = skip_samples;
+                        new_frame_size -= skip_samples+lookahead;
+                        frame_offset = skip_samples+lookahead;
                      }
                      if (packet_no == page_nb_packets && skip_samples < 0)
                      {
-                        int packet_length = nframes*frame_size+skip_samples;
+                        int packet_length = nframes*frame_size+skip_samples+lookahead;
                         new_frame_size = packet_length - j*frame_size;
                         if (new_frame_size<0)
                            new_frame_size = 0;
@@ -701,7 +710,7 @@ int main(int argc, char **argv)
                            new_frame_size = frame_size;
                         /*printf ("chopping end: %d %d %d\n", new_frame_size, packet_length, packet_no);*/
                      }
-                     if (new_frame_size)
+                     if (new_frame_size>0)
                      {  
 #if defined WIN32 || defined _WIN32
                         if (strlen(outFile)==0)