#include #include #include #include #include "base.h" int sp_create(sp_data **spp) { *spp = (sp_data *) malloc(sizeof(sp_data)); sp_data *sp = *spp; sprintf(sp->filename, "test.wav"); sp->nchan = 1; SPFLOAT *out = malloc(sizeof(SPFLOAT) * sp->nchan); *out = 0; sp->out = out; sp->sr = 44100; sp->len = 5 * sp->sr; sp->pos = 0; sp->rand = 0; return 0; } int sp_createn(sp_data **spp, int nchan) { *spp = (sp_data *) malloc(sizeof(sp_data)); sp_data *sp = *spp; sprintf(sp->filename, "test.wav"); sp->nchan = nchan; SPFLOAT *out = malloc(sizeof(SPFLOAT) * sp->nchan); *out = 0; sp->out = out; sp->sr = 44100; sp->len = 5 * sp->sr; sp->pos = 0; sp->rand = 0; return 0; } int sp_destroy(sp_data **spp) { sp_data *sp = *spp; free(sp->out); free(*spp); return 0; } #ifndef NO_LIBSNDFILE int sp_process(sp_data *sp, void *ud, void (*callback)(sp_data *, void *)) { SNDFILE *sf[sp->nchan]; char tmp[140]; SF_INFO info; memset(&info, 0, sizeof(SF_INFO)); SPFLOAT buf[sp->nchan][SP_BUFSIZE]; info.samplerate = sp->sr; info.channels = 1; info.format = SF_FORMAT_WAV | SF_FORMAT_PCM_24; int numsamps, i, chan; if(sp->nchan == 1) { sf[0] = sf_open(sp->filename, SFM_WRITE, &info); } else { for(chan = 0; chan < sp->nchan; chan++) { sprintf(tmp, "%02d_%s", chan, sp->filename); sf[chan] = sf_open(tmp, SFM_WRITE, &info); } } while(sp->len > 0){ if(sp->len < SP_BUFSIZE) { numsamps = sp->len; }else{ numsamps = SP_BUFSIZE; } for(i = 0; i < numsamps; i++){ callback(sp, ud); for(chan = 0; chan < sp->nchan; chan++) { buf[chan][i] = sp->out[chan]; } sp->pos++; } for(chan = 0; chan < sp->nchan; chan++) { #ifdef USE_DOUBLE sf_write_double(sf[chan], buf[chan], numsamps); #else sf_write_float(sf[chan], buf[chan], numsamps); #endif } sp->len -= numsamps; } for(i = 0; i < sp->nchan; i++) { sf_close(sf[i]); } return 0; } #endif int sp_process_raw(sp_data *sp, void *ud, void (*callback)(sp_data *, void *)) { int chan; if(sp->len == 0) { while(1) { callback(sp, ud); for (chan = 0; chan < sp->nchan; chan++) { fwrite(&sp->out[chan], sizeof(SPFLOAT), 1, stdout); } sp->len--; } } else { while(sp->len > 0) { callback(sp, ud); for (chan = 0; chan < sp->nchan; chan++) { fwrite(&sp->out[chan], sizeof(SPFLOAT), 1, stdout); } sp->len--; sp->pos++; } } return SP_OK; } #ifdef USE_SPA int sp_process_spa(sp_data *sp, void *ud, void (*callback)(sp_data *, void *)) { sp_audio spa; if(spa_open(sp, &spa, sp->filename, SPA_WRITE) == SP_NOT_OK) { fprintf(stderr, "Error: could not open file %s.\n", sp->filename); } while(sp->len > 0) { callback(sp, ud); spa_write_buf(sp, &spa, sp->out, sp->nchan); sp->len--; sp->pos++; } spa_close(&spa); return SP_OK; } #endif int sp_process_plot(sp_data *sp, void *ud, void (*callback)(sp_data *, void *)) { int chan; fprintf(stdout, "sp_out = [ ... \n"); while(sp->len > 0) { callback(sp, ud); for (chan = 0; chan < sp->nchan; chan++) { /* fwrite(&sp->out[chan], sizeof(SPFLOAT), 1, stdout); */ fprintf(stdout, "%g ", sp->out[chan]); } fprintf(stdout, "; ...\n"); sp->len--; sp->pos++; } fprintf(stdout, "];\n"); fprintf(stdout, "plot(sp_out);\n"); fprintf(stdout, "title('Plot generated by Soundpipe');\n"); fprintf(stdout, "xlabel('Time (samples)');\n"); fprintf(stdout, "ylabel('Amplitude');\n"); return SP_OK; } int sp_auxdata_alloc(sp_auxdata *aux, size_t size) { aux->ptr = malloc(size); aux->size = size; memset(aux->ptr, 0, size); return SP_OK; } int sp_auxdata_free(sp_auxdata *aux) { free(aux->ptr); return SP_OK; } SPFLOAT sp_midi2cps(SPFLOAT nn) { return pow(2, (nn - 69.0) / 12.0) * 440.0; } int sp_set(sp_param *p, SPFLOAT val) { p->state = 1; p->val = val; return SP_OK; } int sp_out(sp_data *sp, uint32_t chan, SPFLOAT val) { if(chan > sp->nchan - 1) { fprintf(stderr, "sp_out: Invalid channel\n"); return SP_NOT_OK; } sp->out[chan] = val; return SP_OK; } /* uint32_t sp_rand(sp_data *sp) { uint32_t val = (1103515245 * sp->rand + 12345) % SP_RANDMAX; sp->rand = val; return val; } */ void sp_srand(sp_data *sp, uint32_t val) { sp->rand = val; }