1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153
|
#include <stdio.h>
#include <errno.h>
#include "fe.h"
#include "feat.h"
#include "cmd_ln.h"
#include "ckd_alloc.h"
#include "test_macros.h"
int
main(int argc, char *argv[])
{
static const arg_t fe_args[] = {
waveform_to_cepstral_command_line_macro(),
{ NULL, 0, NULL, NULL }
};
FILE *raw;
cmd_ln_t *config;
fe_t *fe;
feat_t *fcb;
int16 buf[2048];
mfcc_t **cepbuf, **cptr;
mfcc_t ***featbuf1, ***featbuf2, ***fptr;
size_t nsamp;
int32 total_frames, ncep, nfr, i;
if ((raw = fopen(TESTDATADIR "/chan3.raw", "rb")) == NULL) {
perror(TESTDATADIR "/chan3.raw");
return 1;
}
config = cmd_ln_parse_r(NULL, fe_args, argc, argv, FALSE);
fe = fe_init_auto_r(config);
fcb = feat_init("1s_c_d_dd", CMN_NONE, FALSE, AGC_NONE,
TRUE, fe_get_output_size(fe));
/* Determine how much data and how many MFCC frames we need. */
fseek(raw, 0, SEEK_END);
nsamp = ftell(raw) / sizeof(int16);
fe_process_frames(fe, NULL, &nsamp, NULL, &total_frames, NULL);
printf("%d samples, %d + 1 frames\n", nsamp, total_frames);
total_frames++; /* For the possible fe_end_utt() frame */
cepbuf = ckd_calloc_2d(total_frames + 1, fe_get_output_size(fe), sizeof(**cepbuf));
fseek(raw, 0, SEEK_SET);
/* Pay close attention, kids. This is how you use fe_process_frames(). */
fe_start_utt(fe);
cptr = cepbuf;
nfr = total_frames;
while ((nsamp = fread(buf, sizeof(int16), 2048, raw)) > 0) {
int16 const *bptr = buf;
while (nsamp) {
int32 ncep = nfr;
fe_process_frames(fe, &bptr, &nsamp, cptr, &ncep, NULL);
cptr += ncep;
nfr -= ncep;
}
}
fe_end_utt(fe, *cptr, &nfr);
/* Now test some feature extraction problems. */
featbuf1 = feat_array_alloc(fcb, total_frames);
featbuf2 = feat_array_alloc(fcb, total_frames);
/* Whole utterance: canonical, assumed to be correct. */
ncep = total_frames;
TEST_EQUAL(total_frames,
feat_s2mfc2feat_live(fcb, cepbuf,
&ncep, TRUE, TRUE,
featbuf1));
TEST_EQUAL(ncep, total_frames);
/* Process one frame at a time. */
cptr = cepbuf;
fptr = featbuf2;
ncep = 1;
nfr = feat_s2mfc2feat_live(fcb, cptr, &ncep, TRUE, FALSE, fptr);
TEST_EQUAL(nfr, 0); /* Not possible to make any frames yet. */
TEST_EQUAL(ncep, 1); /* But we shold have consumed one. */
cptr += ncep;
for (i = 1; i < total_frames - 1; ++i) {
ncep = 1;
nfr = feat_s2mfc2feat_live(fcb, cptr, &ncep, FALSE, FALSE, fptr);
cptr += ncep;
fptr += nfr;
}
nfr = feat_s2mfc2feat_live(fcb, cptr, &ncep, FALSE, TRUE, fptr);
TEST_EQUAL(nfr, 4); /* This should have dumped the trailing window. */
TEST_EQUAL(ncep, 1); /* And only consumed one frame of MFCCs. */
cptr += ncep;
fptr += nfr;
/* Verify that we actually got the correct number of frames. */
TEST_EQUAL(cptr - cepbuf, total_frames);
TEST_EQUAL(fptr - featbuf2, total_frames);
/* Now verify that the results are equal. */
for (i = 0; i < total_frames; ++i) {
int32 j;
printf("%-4d ", i);
for (j = 0; j < feat_dimension(fcb); ++j) {
TEST_EQUAL_FLOAT(featbuf1[i][0][j], featbuf2[i][0][j]);
}
if (i % 10 == 9)
printf("\n");
}
printf("\n");
/* Process large chunks of frames at once, so as to exceed the
* internal ringbuffer size in feat_s2mfc2feat_live(). */
cptr = cepbuf;
fptr = featbuf2;
ncep = total_frames;
nfr = feat_s2mfc2feat_live(fcb, cptr, &ncep, TRUE, FALSE, fptr);
TEST_ASSERT(ncep != nfr);
cptr += ncep;
fptr += nfr;
ncep = total_frames - ncep;
while (ncep) {
int32 tmp_ncep;
tmp_ncep = ncep;
nfr = feat_s2mfc2feat_live(fcb, cptr, &tmp_ncep, FALSE, FALSE, fptr);
cptr += tmp_ncep;
fptr += nfr;
ncep -= tmp_ncep;
}
nfr = feat_s2mfc2feat_live(fcb, cptr, &ncep, FALSE, TRUE, fptr);
cptr += ncep;
fptr += nfr;
TEST_EQUAL(cptr - cepbuf, total_frames);
TEST_EQUAL(fptr - featbuf2, total_frames);
/* Now verify that the results are equal. */
for (i = 0; i < total_frames; ++i) {
int32 j;
printf("%-4d ", i);
for (j = 0; j < feat_dimension(fcb); ++j)
TEST_EQUAL_FLOAT(featbuf1[i][0][j], featbuf2[i][0][j]);
if (i % 10 == 9)
printf("\n");
}
printf("\n");
fclose(raw);
fe_free(fe);
feat_array_free(featbuf1);
feat_array_free(featbuf2);
feat_free(fcb);
ckd_free_2d(cepbuf);
cmd_ln_free_r(config);
return 0;
}
|