annotate src/libsamplerate-0.1.9/examples/timewarp-file.c @ 83:ae30d91d2ffe

Replace these with versions built using an older toolset (so as to avoid ABI compatibilities when linking on Ubuntu 14.04 for packaging purposes)
author Chris Cannam
date Fri, 07 Feb 2020 11:51:13 +0000
parents 481f5f8c5634
children
rev   line source
Chris@41 1 /*
Chris@41 2 ** Copyright (c) 2005-2016, Erik de Castro Lopo <erikd@mega-nerd.com>
Chris@41 3 ** All rights reserved.
Chris@41 4 **
Chris@41 5 ** This code is released under 2-clause BSD license. Please see the
Chris@41 6 ** file at : https://github.com/erikd/libsamplerate/blob/master/COPYING
Chris@41 7 */
Chris@41 8
Chris@41 9 #include "config.h"
Chris@41 10
Chris@41 11 #include <stdio.h>
Chris@41 12 #include <stdlib.h>
Chris@41 13 #include <unistd.h>
Chris@41 14 #include <string.h>
Chris@41 15 #include <math.h>
Chris@41 16
Chris@41 17 #if (HAVE_SNDFILE)
Chris@41 18
Chris@41 19 #include <samplerate.h>
Chris@41 20 #include <sndfile.h>
Chris@41 21
Chris@41 22 #define ARRAY_LEN(x) ((int) (sizeof (x) / sizeof ((x) [0])))
Chris@41 23
Chris@41 24 #define DEFAULT_CONVERTER SRC_SINC_MEDIUM_QUALITY
Chris@41 25
Chris@41 26 #define BUFFER_LEN 1024
Chris@41 27 #define INPUT_STEP_SIZE 8
Chris@41 28
Chris@41 29 typedef struct
Chris@41 30 { sf_count_t index ;
Chris@41 31 double ratio ;
Chris@41 32 } TIMEWARP_FACTOR ;
Chris@41 33
Chris@41 34 static void usage_exit (const char *progname) ;
Chris@41 35 static sf_count_t timewarp_convert (SNDFILE *infile, SNDFILE *outfile, int converter, int channels) ;
Chris@41 36
Chris@41 37 int
Chris@41 38 main (int argc, char *argv [])
Chris@41 39 { SNDFILE *infile, *outfile ;
Chris@41 40 SF_INFO sfinfo ;
Chris@41 41 sf_count_t count ;
Chris@41 42
Chris@41 43 if (argc != 3)
Chris@41 44 usage_exit (argv [0]) ;
Chris@41 45
Chris@41 46 putchar ('\n') ;
Chris@41 47 printf ("Input File : %s\n", argv [argc - 2]) ;
Chris@41 48 if ((infile = sf_open (argv [argc - 2], SFM_READ, &sfinfo)) == NULL)
Chris@41 49 { printf ("Error : Not able to open input file '%s'\n", argv [argc - 2]) ;
Chris@41 50 exit (1) ;
Chris@41 51 } ;
Chris@41 52
Chris@41 53 if (INPUT_STEP_SIZE * sfinfo.channels > BUFFER_LEN)
Chris@41 54 { printf ("\n\nError : INPUT_STEP_SIZE * sfinfo.channels > BUFFER_LEN\n\n") ;
Chris@41 55 exit (1) ;
Chris@41 56 } ;
Chris@41 57
Chris@41 58
Chris@41 59 /* Delete the output file length to zero if already exists. */
Chris@41 60 remove (argv [argc - 1]) ;
Chris@41 61
Chris@41 62 if ((outfile = sf_open (argv [argc - 1], SFM_WRITE, &sfinfo)) == NULL)
Chris@41 63 { printf ("Error : Not able to open output file '%s'\n", argv [argc - 1]) ;
Chris@41 64 sf_close (infile) ;
Chris@41 65 exit (1) ;
Chris@41 66 } ;
Chris@41 67
Chris@41 68 sf_command (outfile, SFC_SET_CLIPPING, NULL, SF_TRUE) ;
Chris@41 69
Chris@41 70 printf ("Output file : %s\n", argv [argc - 1]) ;
Chris@41 71 printf ("Converter : %s\n", src_get_name (DEFAULT_CONVERTER)) ;
Chris@41 72
Chris@41 73 count = timewarp_convert (infile, outfile, DEFAULT_CONVERTER, sfinfo.channels) ;
Chris@41 74
Chris@41 75 printf ("Output Frames : %ld\n\n", (long) count) ;
Chris@41 76
Chris@41 77 sf_close (infile) ;
Chris@41 78 sf_close (outfile) ;
Chris@41 79
Chris@41 80 return 0 ;
Chris@41 81 } /* main */
Chris@41 82
Chris@41 83 /*==============================================================================
Chris@41 84 */
Chris@41 85
Chris@41 86 static TIMEWARP_FACTOR warp [] =
Chris@41 87 { { 0 , 1.00000001 },
Chris@41 88 { 20000 , 1.01000000 },
Chris@41 89 { 20200 , 1.00000001 },
Chris@41 90 { 40000 , 1.20000000 },
Chris@41 91 { 40300 , 1.00000001 },
Chris@41 92 { 60000 , 1.10000000 },
Chris@41 93 { 60400 , 1.00000001 },
Chris@41 94 { 80000 , 1.50000000 },
Chris@41 95 { 81000 , 1.00000001 },
Chris@41 96 } ;
Chris@41 97
Chris@41 98 static sf_count_t
Chris@41 99 timewarp_convert (SNDFILE *infile, SNDFILE *outfile, int converter, int channels)
Chris@41 100 { static float input [BUFFER_LEN] ;
Chris@41 101 static float output [BUFFER_LEN] ;
Chris@41 102
Chris@41 103 SRC_STATE *src_state ;
Chris@41 104 SRC_DATA src_data ;
Chris@41 105 int error, warp_index = 0 ;
Chris@41 106 sf_count_t input_count = 0, output_count = 0 ;
Chris@41 107
Chris@41 108 sf_seek (infile, 0, SEEK_SET) ;
Chris@41 109 sf_seek (outfile, 0, SEEK_SET) ;
Chris@41 110
Chris@41 111 /* Initialize the sample rate converter. */
Chris@41 112 if ((src_state = src_new (converter, channels, &error)) == NULL)
Chris@41 113 { printf ("\n\nError : src_new() failed : %s.\n\n", src_strerror (error)) ;
Chris@41 114 exit (1) ;
Chris@41 115 } ;
Chris@41 116
Chris@41 117 src_data.end_of_input = 0 ; /* Set this later. */
Chris@41 118
Chris@41 119 /* Start with zero to force load in while loop. */
Chris@41 120 src_data.input_frames = 0 ;
Chris@41 121 src_data.data_in = input ;
Chris@41 122
Chris@41 123 if (warp [0].index > 0)
Chris@41 124 src_data.src_ratio = 1.0 ;
Chris@41 125 else
Chris@41 126 { src_data.src_ratio = warp [0].ratio ;
Chris@41 127 warp_index ++ ;
Chris@41 128 } ;
Chris@41 129
Chris@41 130 src_data.data_out = output ;
Chris@41 131 src_data.output_frames = BUFFER_LEN /channels ;
Chris@41 132
Chris@41 133 while (1)
Chris@41 134 {
Chris@41 135 if (warp_index < ARRAY_LEN (warp) - 1 && input_count >= warp [warp_index].index)
Chris@41 136 { src_data.src_ratio = warp [warp_index].ratio ;
Chris@41 137 warp_index ++ ;
Chris@41 138 } ;
Chris@41 139
Chris@41 140 /* If the input buffer is empty, refill it. */
Chris@41 141 if (src_data.input_frames == 0)
Chris@41 142 { src_data.input_frames = sf_readf_float (infile, input, INPUT_STEP_SIZE) ;
Chris@41 143 input_count += src_data.input_frames ;
Chris@41 144 src_data.data_in = input ;
Chris@41 145
Chris@41 146 /* The last read will not be a full buffer, so snd_of_input. */
Chris@41 147 if (src_data.input_frames < INPUT_STEP_SIZE)
Chris@41 148 src_data.end_of_input = SF_TRUE ;
Chris@41 149 } ;
Chris@41 150
Chris@41 151 /* Process current block. */
Chris@41 152 if ((error = src_process (src_state, &src_data)))
Chris@41 153 { printf ("\nError : %s\n", src_strerror (error)) ;
Chris@41 154 exit (1) ;
Chris@41 155 } ;
Chris@41 156
Chris@41 157 /* Terminate if done. */
Chris@41 158 if (src_data.end_of_input && src_data.output_frames_gen == 0)
Chris@41 159 break ;
Chris@41 160
Chris@41 161 /* Write output. */
Chris@41 162 sf_writef_float (outfile, output, src_data.output_frames_gen) ;
Chris@41 163 output_count += src_data.output_frames_gen ;
Chris@41 164
Chris@41 165 src_data.data_in += src_data.input_frames_used * channels ;
Chris@41 166 src_data.input_frames -= src_data.input_frames_used ;
Chris@41 167 } ;
Chris@41 168
Chris@41 169 src_delete (src_state) ;
Chris@41 170
Chris@41 171 return output_count ;
Chris@41 172 } /* timewarp_convert */
Chris@41 173
Chris@41 174 /*------------------------------------------------------------------------------
Chris@41 175 */
Chris@41 176
Chris@41 177 static void
Chris@41 178 usage_exit (const char *progname)
Chris@41 179 { const char *cptr ;
Chris@41 180
Chris@41 181 if ((cptr = strrchr (progname, '/')) != NULL)
Chris@41 182 progname = cptr + 1 ;
Chris@41 183
Chris@41 184 if ((cptr = strrchr (progname, '\\')) != NULL)
Chris@41 185 progname = cptr + 1 ;
Chris@41 186
Chris@41 187 printf ("\n"
Chris@41 188 " A program demonstrating the time warping capabilities of libsamplerate."
Chris@41 189 " It uses libsndfile for file I/O and Secret Rabbit Code (aka libsamplerate)"
Chris@41 190 " for performing the warping.\n"
Chris@41 191 " It works on any file format supported by libsndfile with any \n"
Chris@41 192 " number of channels (limited only by host memory).\n"
Chris@41 193 "\n"
Chris@41 194 " The warping is dependant on a table hard code into the source code.\n"
Chris@41 195 "\n"
Chris@41 196 " libsamplerate version : %s\n"
Chris@41 197 "\n"
Chris@41 198 " Usage : \n"
Chris@41 199 " %s <input file> <output file>\n"
Chris@41 200 "\n", src_get_version (), progname) ;
Chris@41 201
Chris@41 202 puts ("") ;
Chris@41 203
Chris@41 204 exit (1) ;
Chris@41 205 } /* usage_exit */
Chris@41 206
Chris@41 207 /*==============================================================================
Chris@41 208 */
Chris@41 209
Chris@41 210 #else /* (HAVE_SNFILE == 0) */
Chris@41 211
Chris@41 212 /* Alternative main function when libsndfile is not available. */
Chris@41 213
Chris@41 214 int
Chris@41 215 main (void)
Chris@41 216 { puts (
Chris@41 217 "\n"
Chris@41 218 "****************************************************************\n"
Chris@41 219 " This example program was compiled without libsndfile \n"
Chris@41 220 " (http://www.mega-nerd.com/libsndfile/).\n"
Chris@41 221 " It is therefore completely broken and non-functional.\n"
Chris@41 222 "****************************************************************\n"
Chris@41 223 "\n"
Chris@41 224 ) ;
Chris@41 225
Chris@41 226 return 0 ;
Chris@41 227 } /* main */
Chris@41 228
Chris@41 229 #endif
Chris@41 230