Mercurial > hg > aim92
view xaim/synthdramp.c @ 0:5242703e91d3 tip
Initial checkin for AIM92 aimR8.2 (last updated May 1997).
author | tomwalters |
---|---|
date | Fri, 20 May 2011 15:19:45 +0100 |
parents | |
children |
line wrap: on
line source
/* synthdramp * ------------ * * (A tidied-up version of makeping) * * original: M. Akeroyd. Autumn 1992. * * revisions: roy: 3dec92: decay parameter is now half-life. * MAA: sep93: tidied up the code, got rid of the .h file * * MAA: February 1994: added floor values. * MAA: March 1994: Added initial offsets, and 'steps' */ #include <stdio.h> #include <stdlib.h> #include <string.h> #include <math.h> /* the following used to be in "makeping.h" */ #define PulseFreqDef 40 /* Hz */ #define SinFreqDef 800 /* carrier freq: Hz */ #define SampRateDef 20000 /* sampling rate: samples per sec */ #define SinPhaseDef 0.0 /* of carrier wrt to pulse: degrees */ #define AmpMaxDef 10000 /* max amplitude */ #define NoOfPulsesDef 20 /* how many to make */ #define MaxNoSamplesPerWave 882000 /* limit on array size */ #define DampCoefDef 5.0 /* half-life; msecs */ #define FileNameDef "nofilespecified" #define FORWARD 2 /* "forward" == damp, */ #define BACKWARD 3 /* "backward" == ramp. * (for historical reasons). */ #define ON 1 #define OFF 0 #define PI 3.141592654 /*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/ main(int argc, char *argv[]) { int x = 1; int helpflag = OFF; int gateoption = OFF; int toneflag = OFF; int floorflag = OFF; long pulsefreq = PulseFreqDef; long sinfreq = SinFreqDef; long samprate = SampRateDef; long ampmax = AmpMaxDef; double sinphase = SinPhaseDef; long noofpulses = NoOfPulsesDef; double dampcoef = (double) DampCoefDef; int directionflag = FORWARD; short sample_short[MaxNoSamplesPerWave]; /* the array of data ... */ char *filename = FileNameDef; FILE *filepointer; long sampleno, localsampleno, lengthwave_samples; double lengthpulse_samples; double phaserad; double expfactor; double temp; double lengthwave; double sinfreqrad; int floor = 0; int offset_ms = 0; int phase_deg = 0; long offset_samples = 0; double fraction = 0.0; long temp_samples = 0; int delay_ms = 0; long delay_samples = 0; /*---------------------------------------------------------*/ /* Options handler. Hack but it works. * .................................... */ /* special hack for '-h' */ if ((argc ==2) && (!strcmp(argv[1], "-h"))) { argc=1; /* to bypass the upcoming 'while' */ helpflag=ON;} while (x < argc ) { if (!strcmp(argv[x], "-p")) { pulsefreq=atol(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-f")) { sinfreq=atol(argv[x+1]); x += 2; } else if (!strcmp(argv[x], "-s")) { samprate=atol(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-w")) { sinphase=atof(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-m")) { ampmax=atol(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-n")) { noofpulses=atof(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-h")) { dampcoef=atof(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-floor")) { floorflag=ON; floor=atoi(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-offset")) { offset_ms=atoi(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-delay")) { delay_ms=atoi(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-phase")) { phase_deg=atoi(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-frac")) { fraction=atof(argv[x+1]); x += 2;} else if (!strcmp(argv[x], "-t")) { toneflag=ON; x += 1;} else if (!strcmp(argv[x], "-o")) { filename=argv[x+1]; x+=2;} else if (!strcmp(argv[x], "-d")) { directionflag=FORWARD; x+=1;} else if (!strcmp(argv[x], "-r")) { directionflag=BACKWARD; x+=1;} else if (!strcmp(argv[x], "-help")) { helpflag=ON; x+=1;} else if (!strcmp(argv[x], "-g")) { gateoption=ON; x+=1;} else { printf("\nUnknown Option : %s \n", argv[x]); return 1;} } if ((helpflag == ON) || (argc == 1)) {printf("\n ---------- synthdramp (Winter 1994) --------------\n"); printf("\n"); printf("Tone options : \n"); printf(" -w <flt> phase of sin wave, wrt begining of pulse default: %3.3f degs\n", SinPhaseDef); printf(" -f <int> carrier frequency default: %d Hz\n", SinFreqDef); printf("\n"); printf("Gate options : \n"); printf(" -d damped sinusoid (default)\n"); printf(" -r ramped sinusoid \n"); printf(" -s <int> sampling rate default: %d samp/sec\n", SampRateDef); printf(" -m <int> max amplitude default: %d \n", AmpMaxDef); printf(" -n <int> number of cycles in train default: %d \n", NoOfPulsesDef); printf(" -h <flt> half-life default: %3.3f \n", DampCoefDef); printf(" -p <int> repitition rate default: %d Hz\n", PulseFreqDef); printf(" -floor <int> floor value default: %d \n", floor); printf(" -delay <int> delay at begining (ms) default: %d \n", delay_ms); printf("\n"); printf("'Step' options (only work if just gate is created): \n"); printf(" -offset <int> offset time to step (ms) default: %d \n", offset_ms); printf(" -phase <int> offset, measured as phase delay default: %d degrees\n", phase_deg); printf(" -frac <flt> fractional height of step default: 3.3f \n", fraction); printf("\n"); printf("Output options : \n"); printf(" -g gate only : no tone\n"); printf(" -t tone only : no gate\n"); printf(" -o '' output filename \n"); printf("\n"); exit(-1); } if (!strcmp(FileNameDef, filename)) { fprintf(stderr, "\n No file has been specified. Stopping. \n\n"); exit(-1); } /*---------------------------------------------------------*/ /* convert the damping coeeficent from a half-life to whatever the internal * value is. * roy 23-11-92 thru 3-12-92) */ dampcoef = 0.693147/(dampcoef/1000) ; /* define useful things: * lengthwave: overall length of wave, in seconds. * lengthwave_samples: overlall length of wave, in samples. * lengthpulse_samples: length of each pulse, in samples. * phaserad: the phase angle, in radians as against degrees. * sinfreqrad: constant to speed the code up. */ lengthwave = (double) noofpulses / pulsefreq; lengthwave_samples = (long) samprate * noofpulses / pulsefreq; lengthpulse_samples = (double) samprate / pulsefreq; phaserad = sinphase * PI / 180; sinfreqrad = (double) 2 * PI * sinfreq; /* error-check */ if (lengthwave_samples >= MaxNoSamplesPerWave) { fprintf(stderr, "Wave too long for internal arrays. \n"); exit(-1);} /*---------------------------------------------------------*/ /* delay */ for (sampleno=0; sampleno < lengthwave_samples; sampleno++) sample_short[sampleno] = (short) 0; filepointer = fopen(filename, "w"); if (delay_ms != 0) { delay_samples = (long) samprate * delay_ms / 1000; fwrite(sample_short, 2, delay_samples, filepointer);} for (sampleno=0; sampleno < lengthwave_samples; sampleno++) sample_short[sampleno] = (short) 0; /*---------------------------------------------------------*/ /* for each sample, from 0 to the end, work out its value by (1) taking the * value of the carrier, and (2) multiplying it by the exp factor. * if the "-g" option has been called, then in effect make the exp "gate" * only ... * The results go into sample_short[]. */ /*---------------------------*/ for (sampleno=0; sampleno < lengthwave_samples; sampleno++) { temp = (double) (fmod(sampleno, lengthpulse_samples)) / samprate; expfactor = exp( -1 * dampcoef * temp ) ; /* * samprate roy */ if (directionflag == FORWARD) localsampleno = sampleno; else localsampleno = lengthwave_samples -2 - sampleno; /* -2 seems to work */ sample_short[localsampleno]= ampmax * sin(sinfreqrad * temp + phaserad) * expfactor; if (gateoption == ON) sample_short[localsampleno] = ampmax * expfactor; if (floorflag == ON) if (sample_short[localsampleno] <= floor ) sample_short[localsampleno] = (short) floor; } if (toneflag == ON) { for (sampleno=0; sampleno < lengthwave_samples; sampleno++) { temp = (double) (sampleno) / samprate; expfactor=1; sample_short[sampleno]= ampmax * sin(sinfreqrad * temp + phaserad) * expfactor;}} /*---------------------------*/ /* Only do this is step specified: ie, offset or phase ! = 0 */ offset_samples = (long) 0; if (offset_ms != 0) offset_samples = (long) samprate * offset_ms / 1000; if (phase_deg != 0) offset_samples = (long) lengthpulse_samples * phase_deg / 360; if (offset_samples != 0) { for (sampleno=0; sampleno < lengthwave_samples; sampleno++) { temp = (double) (fmod(sampleno, lengthpulse_samples)) / samprate; expfactor = exp( -1 * dampcoef * temp ) ; /* * samprate roy */ if (directionflag == FORWARD) localsampleno = sampleno; else localsampleno = lengthwave_samples -2 - sampleno; /* -2 seems to work */ temp_samples = (long) fmod(sampleno, lengthpulse_samples); if (temp_samples <= offset_samples) sample_short[localsampleno] = sample_short[localsampleno]; else /* sample_short[localsampleno]= fraction * ampmax * sin(sinfreqrad * temp + phaserad) * expfactor + sample_short[localsampleno]; * * if (gateoption == ON)*/ sample_short[localsampleno] = fraction * ampmax * expfactor + sample_short[localsampleno]; }} /*---------------------------------------------------------*/ fwrite(sample_short, 2, lengthwave_samples, filepointer); fclose(filepointer); exit(0); } /* the end */