int main( int argc, char** argv ) { int val = atoi( argv[1] ); printf( "reversed: %i\n", reverse_int( val ) ); printf( "reversed2: %i\n", reverse_int2( val ) ); printf( "\n" ); }
off_t _writeit(int fno) { int i; off_t n=0; short tisamp,*tibuf; float tfsamp,*tfbuf; float peakval; if(!status[fno]) { rtcmix_warn(NULL, "File %d is write-protected!\n",fno); closesf(); } #ifdef OLDRT /* to play before writing */ if((sfclass(&sfdesc[fno]) == SF_SHORT) && play_is_on) playbuf(sndbuf[fno],nbytes/SF_SHORT); /* swap and/or play floating point files */ if(play_is_on && (sfclass(&sfdesc[fno]) == SF_FLOAT)) { peakval = getpeakval(peakflag,fno); playfbuf(sndbuf[fno],peakval,swap_bytes[fno],nbytes/SF_FLOAT); } else { /* just swap if necessary */ if(swap_bytes[fno] && (sfclass(&sfde sc[fno]) == SF_FLOAT)) bytrev4(sndbuf[fno],nbytes); } #endif if(swap_bytes[fno]) { /* SHORT file */ if(sfclass(&sfdesc[fno]) == SF_SHORT) { tibuf = (short *)sndbuf[fno]; for (i=0;i<nbytes/SF_SHORT;i++) { tisamp = *(tibuf+i); *(tibuf+i) = (short) reverse_int2(&tisamp); } } /* FLOAT file */ if(sfclass(&sfdesc[fno]) == SF_FLOAT) { tfbuf = (float *)sndbuf[fno]; for (i=0;i<nbytes/SF_FLOAT;i++) { /* byte_reverse4(tfbuf+i); */ /* tfsamp = *(tfbuf+i); */ /* *(tfbuf+i) = (float) reverse_int4(&tfsamp); */ tfsamp = *(tfbuf+i); byte_reverse4(&tfsamp); *(tfbuf+i) = tfsamp; } } } if(play_is_on < 2) { if((n = write(sfd[fno],sndbuf[fno],nbytes)) != nbytes) { rtcmix_warn("CMIX", "Bad UNIX write, file %d, nbytes = %lld\n",fno,(long long)n); perror("write"); closesf(); } /* update output file size */ if((filepointer[fno] += nbytes) > originalsize[fno]) originalsize[fno] = filepointer[fno]; } if(!play_is_on) printf("."); return(n); }
off_t _readit(int fno) { int i; off_t n, maxread; short tisamp,*tibuf; float tfsamp,*tfbuf; /* check to see if we are attempting to read beyond current * EOF, and if so adjust amount to be read and flush rest of buffer */ /* From make warnings */ n=0; if(filepointer[fno] > originalsize[fno]) maxread = 0; else if((filepointer[fno]+nbytes) > originalsize[fno]) maxread = originalsize[fno]-filepointer[fno]; else maxread = nbytes; if((play_is_on < 3) || (status[fno] == 0)) { if((n = read(sfd[fno],sndbuf[fno],maxread)) != maxread) { if(!n) { /*if(istape[fno] && n) continue;*/ perror("read"); rtcmix_warn("CMIX", "Bad UNIX read, nbytes = %lld\n",(long long)n); rtcmix_warn(NULL, " sfd[fno]= %d\n",sfd[fno]); closesf(); } } } if(((play_is_on==2) && !maxread) || ((play_is_on==3) && (status[fno]))) memset(sndbuf[fno],'\0',nbytes); /* clean buffer out if not readin */ /* Swap input buffer */ if(maxread && swap_bytes[fno]) { /* SHORT file */ if(sfclass(&sfdesc[fno]) == SF_SHORT) { tibuf = (short *)sndbuf[fno]; for (i=0;i<nbytes/SF_SHORT;i++) { tisamp = *(tibuf+i); *(tibuf+i) = reverse_int2(&tisamp); } } /* FLOAT file */ if(sfclass(&sfdesc[fno]) == SF_FLOAT) { tfbuf = (float *)sndbuf[fno]; for (i=0;i<nbytes/SF_FLOAT;i++) { /* byte_reverse4(tfbuf+i); */ /* tfsamp = *(tfbuf+i); */ /* *(tfbuf+i) = (float)reverse_int4(&tfsamp); */ tfsamp = *(tfbuf+i); byte_reverse4(&tfsamp); *(tfbuf+i) = tfsamp; } } } /* if we haven't read in full buffer, zero out rest of buffer, * and adjust filepointer with lseek. Otherwise just update * filepointer. This will position pointer properly for any * situation. Only a write will change physical size of file. */ if(play_is_on < 2) { if(maxread < nbytes) { for(n=maxread; n<nbytes; n++) *(sndbuf[fno] + n) = 0; filepointer[fno] = lseek(sfd[fno],(nbytes-maxread),1); } else filepointer[fno] += nbytes; } else filepointer[fno] += nbytes; return(maxread ? n : maxread); }
int endnote(int xno) { struct timeval tp; struct timezone tzp; int i,j,final_bytes,fno; float notepeak,*pk; double total; long *pkloc; struct tms timbuf; float peakval; struct stat st; short tisamp,*tibuf; float tfsamp,*tfbuf; fno = ABS(xno); /* if fno is negative it means don't write final buffer,just pretend to */ if(wipe_is_off[fno]) _backup(fno); /* else _flushbuf(fno); */ if(!peakoff[fno]) _chkpeak(fno); final_bytes = pointer[fno] * sfclass(&sfdesc[fno]); /* This was DS's and PL's version of real time */ /* Not used in this version */ #ifdef OLDRT /* SHOULD NOT PLAY HERE -- LAST BUFFERS ALREADY PLAYED */ if ((sfclass(&sfdesc[fno]) == SF_SHORT) && play_is_on) playbuf(sndbuf[fno],final_bytes/SF_SHORT); else if ((sfclass(&sfdesc[fno]) == SF_FLOAT) && play_is_on) { peakval = getpeakval(peakflag,fno); playfbuf(sndbuf[fno],peakval,swap[fno],nbytes/SF_FLOAT); } #endif /* write out only fractional part of last record, god bless unix!*/ if(pointer[fno] && (play_is_on < 2)) { if(xno >= 0) { /* Swap bytes if necessary */ if(final_bytes && swap_bytes[fno]) { /* SHORT file */ if(sfclass(&sfdesc[fno]) == SF_SHORT) { tibuf = (short *)sndbuf[fno]; for (i=0;i<final_bytes/SF_SHORT;i++) { tisamp = *(tibuf+i); *(tibuf+i) = reverse_int2(&tisamp); } } /* FLOAT file */ if(sfclass(&sfdesc[fno]) == SF_FLOAT) { tfbuf = (float *)sndbuf[fno]; for (i=0;i<final_bytes/SF_FLOAT;i++) { /* byte_reverse4(tfbuf+i); */ /* tfsamp = *(tfbuf+i); */ /* *(tfbuf+i) = (float)reverse_int4(&tfsamp); */ tfsamp = *(tfbuf+i); byte_reverse4(&tfsamp); *(tfbuf+i) = tfsamp; } } } if((i = write(sfd[fno],sndbuf[fno],final_bytes)) != final_bytes) { rtcmix_warn("CMIX", "Bad UNIX write, file %d, nbytes = %d\n", fno,i); perror("write"); closesf(); } } if((filepointer[fno] += final_bytes) > originalsize[fno]) if(xno >0) originalsize[fno] = filepointer[fno]; } /* DT: if(play_is_on) flush_buffers(); */ pk = (float *)peak[fno]; pkloc = (long *)peakloc[fno]; total = ((double)filepointer[fno]-headersize[fno]) /((double)sfclass(&sfdesc[fno])) /(double)sfchans(&sfdesc[fno])/SR(); /* _writeit(fno); write out final record */ for(i = 0,notepeak=0; i<sfchans(&sfdesc[fno]); i++) { if(*(pk+i) > sfmaxamp(&sfm[fno],i)) { sfmaxamp(&sfm[fno],i) = *(pk+i); sfmaxamploc(&sfm[fno],i) = *(pkloc+i); } if(*(pk+i) > notepeak) notepeak = *(pk+i); } gettimeofday(&tp,&tzp); sfmaxamptime(&sfm[fno]) = tp.tv_sec; if((filepointer[fno] = lseek(sfd[fno],0L,0)) < 0) { rtcmix_warn("CMIX", "Bad lseek to beginning of file\n"); perror("lseek"); closesf(); } times(&timbuf); #ifndef MAXMSP // this really isn't used... printf("\n(%6.2f)",(float)( (timbuf.tms_stime-clockin[fno].tms_stime)+ (timbuf.tms_utime-clockin[fno].tms_utime))/60.); printf(" %9.4f .. %9.4f MM ",starttime[fno],total); if(!peakoff[fno]) { for(j=0;j<sfchans(&sfdesc[fno]);j++) printf(" c%d=%e",j,*(pk+j)); printf("\n"); if(punch[fno]) { printf("alter(%e,%e,%e/%e", (double)starttime[fno],(double)(total-starttime[fno]), punch[fno],notepeak); for(i=0; i<sfchans(&sfdesc[fno]); i++) printf(",1 "); printf(")\n"); printf("mix(%g,%g,%g,%g/%g", (double)starttime[fno],(double)starttime[fno],-(double)(total-starttime[fno]),punch[fno],notepeak); for(i=0; i<sfchans(&sfdesc[fno]); i++) printf(",%d ",i); printf(")\n"); } } #endif // MAXMSP /* Copy the updated peak stats into the SFHEADER struct for this output file. (No swapping necessary.) */ memcpy(&(sfmaxampstruct(&sfdesc[fno])), &sfm[fno], sizeof(SFMAXAMP)); /* Write header to file. */ if (wheader(sfd[fno], &sfdesc[fno])) { rtcmix_warn("endnote", "bad header write\n"); perror("write"); closesf(); } return 0; }
/* Let user load a function table with samples from a sound file. The file can be 16-bit integer or 32-bit floating point in either byte order, and in any of the header formats recognized by sndlib. The makegen syntax used in Minc is: frames_read = makegen(slot, 1, size, filename, inskip [, inchan, dump]) <size> is the duration (in seconds) of the sound file segment, or if it's negative, the number of sample frames to read. If <size> is zero, the whole file is slurpped in. (Beware with large files -- there is no check on memory consumption here!) <filename> is a double-quoted pathname (as in rtinput). <inskip> is the time (in seconds) to skip before reading, or if it's negative, the number of sample frames to skip before reading. If <inchan> is missing, reads all channels from the file; otherwise, reads just the channel specified by <inchan> (with zero as first chan). If <dump> is 1, then dumps the gen table to a header-less sound file, called "dumpaudio.raw," in the current directory. The file is 32-bit float, using the host byte order, <inchan> chans, and the sampling rate in the source file's header. As usual, if the slot number is positive, the table will be rescaled to fit in the range [-1,1]; if it's negative, it will not be rescaled. Returns to Minc the number of sample frames read. JGG, 07 Feb 2001 */ double gen1(struct gen *gen, char *sfname) { int i, fd, header_type, data_format, data_location, inchan; int gen_chans, gen_frames, gen_samps, file_chans, file_frames; int start_frame, bytes_per_samp, byteswap, is_float, dump; int buf_start_frame, end_frame, frames_read, buf_frames; long file_samps; off_t seek_to; float request_dur, filedur, inskip; double srate, *block, *blockp; char *buf; request_dur = gen->pvals[0]; inskip = gen->pvals[2]; if (gen->nargs > 3) inchan = (int) gen->pvals[3]; else inchan = -1; /* read all chans */ dump = gen->nargs > 4? (int) gen->pvals[4] : 0; fd = open_sound_file("gen1", sfname, &header_type, &data_format, &data_location, &srate, &file_chans, &file_samps); if (fd == -1) return die("gen1", "Can't open input file: \"%s\"!", sfname); if (srate != SR()) { rtcmix_warn("gen1", "The input file sampling rate is %g, but " "the output rate is currently %g.", srate, SR()); } file_frames = file_samps / file_chans; if (inchan == -1) gen_chans = file_chans; else gen_chans = 1; if (file_chans == 1) inchan = -1; /* more efficient copy below */ if (inchan >= file_chans) return die("gen1", "You asked for channel %d of a %d-channel file. (\"%s\")", inchan, file_chans, sfname); if (request_dur < 0.0) gen_frames = (int) -request_dur; else if (request_dur > 0.0) gen_frames = (int) (request_dur * srate); else gen_frames = file_frames; if (inskip < 0.0) start_frame = (int) -inskip; else start_frame = (int) (inskip * srate); if (start_frame + gen_frames > file_frames) gen_frames = file_frames - start_frame; gen_samps = gen_frames * gen_chans; block = (double *) malloc((size_t) (gen_samps * sizeof(double))); if (block == NULL) return die("gen1", "Not enough memory for function table %d.", gen->slot); buf = (char *) malloc((size_t) BUFSIZE); if (buf == NULL) { free(block); return die("gen1", "Not enough memory for temporary buffer."); } bytes_per_samp = mus_data_format_to_bytes_per_sample(data_format); seek_to = data_location + (start_frame * file_chans * bytes_per_samp); if (lseek(fd, seek_to, SEEK_SET) == -1) { free(block); free(buf); return die("gen1", "lseek() failed"); } #if MUS_LITTLE_ENDIAN byteswap = IS_BIG_ENDIAN_FORMAT(data_format); #else byteswap = IS_LITTLE_ENDIAN_FORMAT(data_format); #endif is_float = IS_FLOAT_FORMAT(data_format); buf_frames = (BUFSIZE / bytes_per_samp) / file_chans; end_frame = start_frame + gen_frames; blockp = block; frames_read = 0; buf_start_frame = start_frame; for ( ; buf_start_frame < end_frame; buf_start_frame += frames_read) { int samps_read; long bytes_read; if (buf_start_frame + buf_frames > end_frame) { /* last buffer */ int samps = (end_frame - buf_start_frame) * file_chans; bytes_read = read(fd, buf, samps * bytes_per_samp); } else bytes_read = read(fd, buf, BUFSIZE); if (bytes_read == -1) { free(block); free(buf); return die("gen1", "read() failed"); } if (bytes_read == 0) /* EOF, somehow */ break; samps_read = bytes_read / bytes_per_samp; frames_read = samps_read / file_chans; if (is_float) { float *bufp = (float *) buf; if (inchan == -1) { /* store all chans */ if (byteswap) { for (i = 0; i < samps_read; i++) { byte_reverse4(bufp); /* modify *bufp in place */ *blockp++ = (double) *bufp++; } } else { for (i = 0; i < samps_read; i++) *blockp++ = (double) *bufp++; } } else { /* store only inchan */ bufp += inchan; if (byteswap) { for (i = 0; i < samps_read; i += file_chans) { byte_reverse4(bufp); /* modify *bufp in place */ *blockp++ = (double) *bufp; bufp += file_chans; } } else { for (i = 0; i < samps_read; i += file_chans) { *blockp++ = (double) *bufp; bufp += file_chans; } } } } else { /* is shortint file */ short *bufp = (short *) buf; if (inchan == -1) { /* store all chans */ if (byteswap) { for (i = 0; i < samps_read; i++, bufp++) { short samp = reverse_int2(bufp); *blockp++ = (double) samp; } } else { for (i = 0; i < samps_read; i++) *blockp++ = (double) *bufp++; } } else { /* store only inchan */ bufp += inchan; if (byteswap) { for (i = 0; i < samps_read; i += file_chans) { short samp = reverse_int2(bufp); *blockp++ = (double) samp; bufp += file_chans; } } else { for (i = 0; i < samps_read; i += file_chans) { *blockp++ = (double) *bufp; bufp += file_chans; } } } } } free(buf); sndlib_close(fd, 0, 0, 0, 0); gen->array = block; gen->size = gen_samps; fnscl(gen); if (dump) dump_gen_to_raw_file(block, gen_samps); return (double) gen_frames; }
static int getisample(double sampleno, float *c, int input) { ssize_t RECSIZE = bufsize[input]; ssize_t BPREC = RECSIZE * sizeof(short); ssize_t BPFRAME = sfchans(&sfdesc[input]) * sizeof(short); ssize_t FPREC = RECSIZE/sfchans(&sfdesc[input]); int sample,i,j; ssize_t nbytes; signed short *array = (short *)sndbuf[input]; float tempsample1; float tempsample2; float fraction; static int oldsample = 0; static int endsample = 0; sample = (int)sampleno; fraction = sampleno - (double)sample; if(!((sample >= oldsample) && (sample < endsample))) { /* sflseek (sfheader.h) assumes header size, so can't use it */ if(lseek(sfd[input], (sample * BPFRAME) + headersize[input], SEEK_SET) <= 0) { rterror(NULL, "badlseek on inputfile\n"); closesf(); } nbytes = read(sfd[input], (char *)array, BPREC); if (nbytes == -1) { perror("getisample: read"); return 0; } if (nbytes == 0) { rterror(NULL, "reached eof on input file\n"); return 0; } if (nbytes < BPREC) { /* zero out rest of sndbuf */ ssize_t n; for (n = nbytes; n < BPREC; n++) sndbuf[input][n] = 0; } oldsample = sample; endsample = oldsample + FPREC - 1; } for(i=(sample-oldsample)*sfchans(&sfdesc[input]),j=0; j<sfchans(&sfdesc[input]); i++,j++) { if (swap_bytes[input]) { tempsample1 = (signed short)reverse_int2(array+i); tempsample2 = (signed short)reverse_int2(array+i+sfchans(&sfdesc[input])); *(c+j) = tempsample1 + fraction * ((float)((signed short)tempsample2 - tempsample1)); } else { *(c+j) = (float)*(array+i) + fraction * ((float) *(array+i+sfchans(&sfdesc[input])) - (float) *(array+i)); } } return(1); }