/*--------------------------------------------------------------------------------*/ void clean_rows_2pass(float *vec, size_t nchan, size_t ndata) { float **dat=(float **)malloc(sizeof(float *)*nchan); for (int i=0;i<nchan;i++) dat[i]=vec+i*ndata; float *tot=vector(ndata); memset(tot,0,sizeof(tot[0])*ndata); //find the common mode based on averaging over channels. //inner loop is the natural one to parallelize over, but for some //architectures/compilers doing so with a omp for is slow, hence //rolling my own. #pragma omp parallel shared(ndata,nchan,dat,tot) default(none) { int imin,imax; get_omp_iminmax(ndata,&imin,&imax); for (int i=0;i<nchan;i++) for (int j=imin;j<imax;j++) tot[j]+=dat[i][j]; for (int j=imin;j<imax;j++) tot[j]/=nchan; } //#define BURST_DUMP_DEBUG #ifdef BURST_DUMP_DEBUG FILE *outfile=fopen("common_mode_1.dat","w"); fwrite(tot,sizeof(float),ndata,outfile); fclose(outfile); #endif float *amps=vector(nchan); memset(amps,0,sizeof(amps[0])*nchan); float totsqr=0; for (int i=0;i<ndata;i++) totsqr+=tot[i]*tot[i]; //find the best-fit amplitude for each channel #pragma omp parallel for shared(ndata,nchan,dat,tot,amps,totsqr) default(none) for (int i=0;i<nchan;i++) { float myamp=0; for (int j=0;j<ndata;j++) myamp+=dat[i][j]*tot[j]; myamp/=totsqr; //for (int j=0;j<ndata;j++) // dat[i][j]-=tot[j]*myamp; amps[i]=myamp; } #ifdef BURST_DUMP_DEBUG outfile=fopen("mean_responses1.txt","w"); for (int i=0;i<nchan;i++) fprintf(outfile,"%12.4f\n",amps[i]); fclose(outfile); #endif //decide that channels with amplitude between 0.5 and 1.5 are the good ones. //recalculate the common mode based on those guys, with appropriate calibration memset(tot,0,sizeof(tot[0])*ndata); float amp_min=0.5; float amp_max=1.5; #pragma omp parallel shared(ndata,nchan,amps,dat,tot,amp_min,amp_max) default(none) { int imin,imax; get_omp_iminmax(ndata,&imin,&imax); for (int i=0;i<nchan;i++) { if ((amps[i]>amp_min)&&(amps[i]<amp_max)) for (int j=imin;j<imax;j++) tot[j]+=dat[i][j]/amps[i]; } } float tot_sum=0; for (int i=0;i<nchan;i++) if ((amps[i]>amp_min)&&(amps[i]<amp_max)) tot_sum+=1./amps[i]; totsqr=0; for (int i=0;i<ndata;i++) { tot[i]/=tot_sum; totsqr+=tot[i]*tot[i]; } #ifdef BURST_DUMP_DEBUG outfile=fopen("common_mode_2.dat","w"); fwrite(tot,sizeof(float),ndata,outfile); fclose(outfile); { float *chansum=vector(nchan); float *chansumsqr=vector(nchan); #pragma omp parallel for for (int i=0;i<nchan;i++) for (int j=0;j<ndata;j++) { chansum[i]+=dat[i][j]; chansumsqr[i]+=dat[i][j]*dat[i][j]; } outfile=fopen("chan_variances_pre.txt","w"); for (int i=0;i<nchan;i++) fprintf(outfile,"%12.6e\n",sqrt(chansumsqr[i]-chansum[i]*chansum[i]/ndata)); fclose(outfile); free(chansum); free(chansumsqr); } #endif memset(amps,0,sizeof(amps[0])*nchan); #pragma omp parallel for shared(ndata,nchan,amps,dat,tot,totsqr) default(none) for (int i=0;i<nchan;i++) { float myamp=0; for (int j=0;j<ndata;j++) myamp+=dat[i][j]*tot[j]; myamp/=totsqr; amps[i]=myamp; for (int j=0;j<ndata;j++) dat[i][j]-=tot[j]*myamp; } #ifdef BURST_DUMP_DEBUG outfile=fopen("mean_responses2.txt","w"); for (int i=0;i<nchan;i++) fprintf(outfile,"%12.4f\n",amps[i]); fclose(outfile); { float *chansum=vector(nchan); float *chansumsqr=vector(nchan); #pragma omp parallel for for (int i=0;i<nchan;i++) for (int j=0;j<ndata;j++) { chansum[i]+=dat[i][j]; chansumsqr[i]+=dat[i][j]*dat[i][j]; } outfile=fopen("chan_variances_post.txt","w"); for (int i=0;i<nchan;i++) fprintf(outfile,"%12.6e\n",sqrt(chansumsqr[i]-chansum[i]*chansum[i]/ndata)); fclose(outfile); free(chansum); free(chansumsqr); } #endif free(amps); free(tot); }
/* MRQMIN */ void mrqmin(float x[], float y[], float sig[], int ndata, float a[], int ia[], int ma, float **covar, float **alpha, float *chisq, void (*funcs)(float, float [], float *, float [], int), float *alamda) { int j,k,l,m; static int mfit; static float ochisq,*atry,*beta,*da,**oneda; if (*alamda < 0.0) { atry=vector(1,ma); beta=vector(1,ma); da=vector(1,ma); for (mfit=0,j=1;j<=ma;j++) if (ia[j]) mfit++; oneda=matrix(1,mfit,1,1); *alamda=0.001; mrqcof(x,y,sig,ndata,a,ia,ma,alpha,beta,chisq,funcs); ochisq=(*chisq); for (j=1;j<=ma;j++) atry[j]=a[j]; } for (j=0,l=1;l<=ma;l++) { if (ia[l]) { for (j++,k=0,m=1;m<=ma;m++) { if (ia[m]) { k++; covar[j][k]=alpha[j][k]; } } covar[j][j]=alpha[j][j]*(1.0+(*alamda)); oneda[j][1]=beta[j]; } } gaussj(covar,mfit,oneda,1); for (j=1;j<=mfit;j++) da[j]=oneda[j][1]; if (*alamda == 0.0) { covsrt(covar,ma,ia,mfit); free_matrix(oneda,1,mfit,1,1); free_vector(da,1,ma); free_vector(beta,1,ma); free_vector(atry,1,ma); return; } for (j=0,l=1;l<=ma;l++) if (ia[l]) atry[l]=a[l]+da[++j]; mrqcof(x,y,sig,ndata,atry,ia,ma,covar,da,chisq,funcs); if (*chisq < ochisq) { *alamda *= 0.1; ochisq=(*chisq); for (j=0,l=1;l<=ma;l++) { if (ia[l]) { for (j++,k=0,m=1;m<=ma;m++) { if (ia[m]) { k++; alpha[j][k]=covar[j][k]; } } beta[j]=da[j]; a[l]=atry[l]; } } } else { *alamda *= 10.0; *chisq=ochisq; } }
/* Waiting for input capture event (stuck in this loop) */ while (1); /* Program should not go here during normal operation */ return EXIT_FAILURE; } // ***************************************************************************** // ***************************************************************************** // Section: Interrupt Service Routine // ***************************************************************************** // ***************************************************************************** void __attribute__((interrupt(ipl2), vector(_INPUT_CAPTURE_1_VECTOR))) InputCaptureHandler(void) { /* Clear the interrupt flag */ PLIB_INT_SourceFlagClear(INT_ID_0, INT_SOURCE_INPUT_CAPTURE_1); /* Make sure input capture buffer is full before performing a read */ if (!PLIB_IC_BufferIsEmpty(IC_ID_1)) { /* Store the value of the capture event into CaptureTime variable */ CaptureTime = PLIB_IC_Buffer32BitGet(IC_ID_1); } } /*******************************************************************************
/*--------------------------------------------------------------------------------*/ void remove_noisecal(Data *dat, int period, int apply_calib) //, float *cal_facs) { double t1=omp_get_wtime(); float **tot=matrix(dat->raw_nchan, period); float **nn=matrix(dat->raw_nchan, period); memset(nn[0],0,sizeof(nn[0][0])*dat->raw_nchan*period); memset(tot[0],0,sizeof(tot[0][0])*dat->raw_nchan*period); #pragma omp parallel for shared(tot,nn,dat,period) default(none) for (int i=0;i<dat->raw_nchan;i++) { int jj=0; for (int j=0;j<dat->ndata;j++) { //int jj=j%period; tot[i][jj]+=dat->raw_data[i][j]; nn[i][jj]++; jj++; if (jj==period) jj=0; } } for (int i=0;i<dat->raw_nchan;i++) for (int j=0;j<period;j++) tot[i][j]/=nn[i][j]; if (0) { FILE *outfile=fopen("noise_cal_template.txt","w"); for (int i=0;i<dat->raw_nchan;i++) { for (int j=0;j<period;j++) fprintf(outfile,"%14.6e ",tot[i][j]); fprintf(outfile,"\n"); } fclose(outfile); } #pragma omp parallel for shared(tot,dat,period) default(none) for (int i=0;i<dat->raw_nchan;i++) { int jj=0; for (int j=0;j<dat->ndata;j++) { //dat->raw_data[i][j]-=tot[i][j%period]; dat->raw_data[i][j]-=tot[i][jj]; jj++; if (jj==period) jj=0; } } //if (cal_facs) { if (apply_calib) { //printf("doing calibration in remove_noisecal.\n"); int my_phase=find_cal_phase(tot,dat->raw_nchan,period); float *calib=vector(dat->raw_nchan); find_cals(tot,dat->raw_nchan,period,my_phase,calib); //FILE *outfile=fopen("my_cals.txt","w"); //for (int i=0;i<dat->raw_nchan;i++) // fprintf(outfile,"%12.4e\n",calib[i]); //fclose(outfile); #pragma omp parallel for for (int i=0;i<dat->raw_nchan;i++) if (calib[i]>0) for (int j=0;j<dat->ndata;j++) dat->raw_data[i][j]/=calib[i]; free(calib); //memset(cal_facs,0,sizeof(cal_facs[0]*dat->raw_nchan)); //for (int i=0;i<dat->raw_nchan;i++) { // for (int j=0;j<period/2;j++ // } } free(nn[0]); free(nn); free(tot[0]); free(tot); //printf("removed noisecal in %12.4f seconds.\n",omp_get_wtime()-t1); }
// set to scalar void om::set(Float scalarVal) { e2ga::__G2_GENERATED__::set(*this, vector(vector_e1_e2, scalarVal, (Float)0), vector(vector_e1_e2, (Float)0, scalarVal)); }
std::vector<T> generate_random_vector(const size_t size) { std::vector<T> vector(size); std::generate(vector.begin(), vector.end(), rand); return vector; }
You should have received a copy of the GNU General Public License along with foam-extend. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "treeBoundBox.H" #include "ListOps.H" // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // const Foam::scalar Foam::treeBoundBox::great(GREAT); const Foam::treeBoundBox Foam::treeBoundBox::greatBox ( vector(-GREAT, -GREAT, -GREAT), vector(GREAT, GREAT, GREAT) ); const Foam::treeBoundBox Foam::treeBoundBox::invertedBox ( vector(GREAT, GREAT, GREAT), vector(-GREAT, -GREAT, -GREAT) ); //! @cond - skip documentation : local scope only const Foam::label facesArray[6][4] = { {0, 4, 6, 2}, // left
void createParcels ( const fvMesh& mesh, cfdemCloud& sm, const int& parcelSize_, int**& parcelCloud_, double**& parcelPositions_, double**& parcelVelocities_, int*& parcelNparts_, double** & parcelKinStress_, scalar& aveSubQparcel2_, vector& meanParcelVel_, const bool verbose_ ) { if ( parcelSize_ * parcelSize_ * parcelSize_ > sm.numberOfParticles() ) { FatalError << " Number of particles in a parcel > number of particles" << abort(FatalError); } if ( parcelSize_ < 1 ) { FatalError << " Number of particles < 0 in a parcel " << abort(FatalError); } // Number of particles in a parcel int k = parcelSize_ * parcelSize_ * parcelSize_; // Dimensions, exact OR approximate int dim =3; double eps = 0; // Number of points int nPts; nPts = sm.numberOfParticles(); // Data points ANNpointArray dataPts; // Query points ANNpoint queryPt; ANNidxArray nnIdx; // near neighbour indices ANNdistArray dists; // near neighbour distances ANNkd_tree* kdTree; // search structure // Allocate queryPt = annAllocPt(dim); dataPts = annAllocPts(nPts, dim); nnIdx = new ANNidx[k]; dists = new ANNdist[k]; for(int index = 0; index < sm.numberOfParticles(); index++) { dataPts[index][0] = sm.position(index).x(); dataPts[index][1] = sm.position(index).y(); dataPts[index][2] = sm.position(index).z(); } kdTree = new ANNkd_tree(dataPts, nPts, dim); // Initialize sub-parcel agitation aveSubQparcel2_ = 0.; // Initialize parcel velocity meanParcelVel_ = vector(0,0,0); for(int index = 0; index < sm.numberOfParticles(); index++) { // Particle neighbouring search distance scalar sqRad = parcelSize_ * sm.radius(index); queryPt[0] = sm.position(index).x(); queryPt[1] = sm.position(index).y(); queryPt[2] = sm.position(index).z(); kdTree->annkFRSearch( queryPt, // query point sqRad, // squared radius k, // number of the near neighbours to return nnIdx, // nearest neighbor array dists, // dist to near neighbours eps ); int nParts = 0; scalar dist = 0; // Initialize parcel velocities & positions & kinetic stresses for(int j=0;j<3;j++) { parcelVelocities_[index][j] = 0.; parcelPositions_[index][j] = 0.; parcelKinStress_[index][j] = 0.; parcelKinStress_[index][2*j] = 0.; } for (int i = 0; i < k; i++) { parcelCloud_[index][i] = nnIdx[i]; dist = mag( sm.position(nnIdx[i]) - sm.position(index) ) - sqRad; if ( dist < SMALL ) { for(int j=0;j<3;j++) { // Parcel velocity parcelVelocities_[index][j] += sm.velocity(nnIdx[i])[j]; // Parcel center of mass parcelPositions_[index][j] += sm.position(nnIdx[i])[j]; } nParts++; } } for(int j=0;j<3;j++) parcelPositions_[index][j] /= nParts; parcelNparts_[index] = nParts; // Parcel kinetic stresses for(int i = 0; i < parcelNparts_[index]; i++) { int particleID = parcelCloud_[index][i]; // U'xU'x parcelKinStress_[index][0] += ( sm.velocity(particleID)[0] - parcelVelocities_[index][0] ) *( sm.velocity(particleID)[0] - parcelVelocities_[index][0] ); // U'yU'y parcelKinStress_[index][1] += ( sm.velocity(particleID)[1] - parcelVelocities_[index][1] ) *( sm.velocity(particleID)[1] - parcelVelocities_[index][1] ); // U'zU'z parcelKinStress_[index][2] += ( sm.velocity(particleID)[2] - parcelVelocities_[index][2] ) *( sm.velocity(particleID)[2] - parcelVelocities_[index][2] ); // U'xU'y parcelKinStress_[index][3] += ( sm.velocity(particleID)[0] - parcelVelocities_[index][0] ) *( sm.velocity(particleID)[1] - parcelVelocities_[index][1] ); // U'xU'z parcelKinStress_[index][4] += ( sm.velocity(particleID)[0] - parcelVelocities_[index][0] ) *( sm.velocity(particleID)[2] - parcelVelocities_[index][2] ); // U'yU'z parcelKinStress_[index][5] += ( sm.velocity(particleID)[1] - parcelVelocities_[index][1] ) *( sm.velocity(particleID)[2] - parcelVelocities_[index][2] ); } // Mean parcel velocity for(int j=0;j<3;j++) meanParcelVel_[j] += parcelVelocities_[index][j]; // Domain-averaged parcel agitation aveSubQparcel2_ += 1./2. * ( parcelKinStress_[index][0] + parcelKinStress_[index][1] + parcelKinStress_[index][2] ); } for(int j=0;j<3;j++) meanParcelVel_[j] /= sm.numberOfParticles(); if ( verbose_ ) { int index = 0; Info << " Parcel particle list "; for (int i = 0; i < parcelNparts_[index]; i++) { Info << parcelCloud_[index][i] << " " ; } Info << endl; Info << " Parcel center " << parcelPositions_[index][0] << "," << parcelPositions_[index][1] << "," << parcelPositions_[index][2] << endl; Info << " Parcel velocity " << parcelVelocities_[index][0] << "," << parcelVelocities_[index][1] << "," << parcelVelocities_[index][2] << endl; for (int i = 0; i < parcelNparts_[index]; i++) { Info << " Particle " << parcelCloud_[index][i] << endl; Info << " Particle center " << sm.position(parcelCloud_[index][i]) << endl; Info << " Particle velocity " << sm.velocity(parcelCloud_[index][i]) << endl; } } }
void importlinkagepedigree (void) { char minibuf[NAMESIZE]; individual *ind, *ind2; // IDlist *idlist; markerlist *marker; namelist *nl; quanttrait *qt; int i, families, persons, nmarkers, ntraits, code; printf("Number of markers in file: "); InputLine(buf, BUFFERSIZE); nmarkers = atoip(buf); printf("Number of traits in file : "); InputLine(buf, BUFFERSIZE); ntraits = atoip(buf); printf ("Name of linkage pedigree file to input: "); InputLine(buf, BUFFERSIZE); cfopen (buf,"r"); getbuf (); persons = 0; families = 0; if (options->Index[O_CONVERTLINKAGEID]) printf("WARNING: ID's are converted from number to fam-number\n"); while (buf[0] != EOF) { // If empty line then read next line if (!buf[0] || !strpbrk(buf, "0123456789")) { getbuf (); continue; } ind = newperson (); persons++; ind->globalid = persons; ind->localid = persons; strcpy(ind->pedigree, igetstr (buf)); strcpy(ind->id, getstr ()); strcpy(ind->tmpstr1, getstr ()); // Father ID strcpy(ind->tmpstr2, getstr ()); // Mother ID // If conversion of IDs if (options->Index[O_CONVERTLINKAGEID]) { sprintf(minibuf,"%s-%s", ind->pedigree,ind->id); strcpy(ind->id,minibuf); sprintf(minibuf, "%s-%s", ind->pedigree,ind->tmpstr1); strcpy(ind->tmpstr1,minibuf); sprintf(minibuf, "%s-%s", ind->pedigree,ind->tmpstr2); strcpy(ind->tmpstr2,minibuf); } switch (geti ()) { case 1 : ind->sex = S_MALE; break; case 2 : ind->sex = S_FEMALE; break; default : ind->sex = S_UNKNOWN; } // atof(getstr()); for (i = 0 ; i<nmarkers; i++) { marker = cmalloc (sizeof (markerlist)); memset (marker,0,sizeof (markerlist)); marker->allele1 = geti(); marker->allele2 = geti (); addlist(&ind->marker, marker); } // Reading traits for (i = 0 ; i<ntraits; i++) { qt = cmalloc (sizeof (quanttrait)); memset (qt,0,sizeof (quanttrait)); ReadATrait(qt); addlist(&ind->qttrait,qt); } // printf("\n"); getbuf (); } fclose (F); printf ("%d persons from %d pedigree(s) read\n", persons, numberofpedigrees()); code = 0; // Should now fix fathers and mothers forind { ind->father = findperson(ind->tmpstr1); ind->mother = findperson(ind->tmpstr2); // if a person has a father and a mother, then add the // person to the parents lists if (ind->father && ind->mother) { adduniqueidlist (&ind->father->offspring, ind); adduniqueidlist (&ind->father->mate, ind->mother); adduniqueidlist (&ind->mother->offspring, ind); adduniqueidlist (&ind->mother->mate,ind->father); } else if (ind->father || ind->mother) // The person has only one parent { code = 1; sprintf(buf2, "%s has only one parent in pedigree file\n", ind->id); WriteErrorMsg(buf2); } } if (code) printf("ERROR: A least one parent not found in pedigree file\n"); // Fixing sibs forind { for (ind2 = ind->next; ind2; ind2 = ind2->next) { // If same father or mother then add to list of both if (((ind->father == ind2->father) && (ind->father)) || ((ind->mother == ind2->mother) && (ind->mother))) { adduniqueidlist(&ind->sib, ind2); adduniqueidlist(&ind2->sib, ind); } } } // Have now read the file and made the dataset // Should fix the missing parts // This part definately needs some error checking // First set the marker names: for (i=1; i<=nmarkers; i++) { nl = cmalloc (sizeof (namelist)); memset (nl,0,sizeof (namelist)); sprintf(nl->name, "Marker %d",i); addlist(&markernames, nl); } // Then add trait names for (i=1; i<=ntraits; i++) { nl = cmalloc (sizeof (namelist)); memset (nl,0,sizeof (namelist)); sprintf(nl->name, "Trait %d",i); addlist(&traitnames, nl); } InitializeFrequencies(nmarkers); // Initialize order and distances order = ivector(1,nmarkers); invorder = ivector(1,nmarkers); distance = vector(1, nmarkers-1); for (i=1; i<=nmarkers; i++) { order[i] = i; invorder[i] = i; } for (i=1; i<nmarkers; i++) distance[i] = InverseMapFunction(0.1); }
void ReadLinkageParameterFile(void) { int i; int linenr, locinumber; int numloci, risk, xlink, program; int locus_type, num_alleles, nmarkers; char *traitname; char tmpbuf[256]; FreqList *fl; namelist *nl; printf("Name of parameter file: "); InputLine(buf, BUFFERSIZE); // Deletes old info FreeDataInfo(); DeletePedigreeData(); DeleteParameterData(); cfopen (buf,"r"); linenr = 0; locinumber = 1; nmarkers = 0; // Read line 1 ReadNextNonEmptyLine(); numloci = atoip (igetstr (buf)); risk = geti(); xlink = geti(); program = geti(); if (numloci==0) { printf("WARNING: No loci in parameter file\n"); return; } InitializeFrequencies(numloci); freelist(markernames); markernames = 0; // Read line 2 and 3. Not used yet ReadNextNonEmptyLine(); ReadNextNonEmptyLine(); // Saves the order for later strncpy(tmpbuf, buf, sizeof(tmpbuf)); // Read all locus/traits while (locinumber <= numloci) { ReadNextNonEmptyLine(); locus_type = atoip (igetstr (buf)); num_alleles = geti(); traitname = GetRestOfLine(); switch (locus_type) { case 1 : break; case 3 : // Read a marker locus fl = FrequencyNumber(locinumber); fl->num_alleles = num_alleles; // Read in the allele frequencies ReadNextNonEmptyLine(); fl->frequency[1] = atof(igetstr(buf)); for (i=2; i<= num_alleles; i++) { fl->frequency[i] = getf(); } // Increase the number of markers in the dataset nmarkers++; // Saves the marker name nl = cmalloc(sizeof(namelist)); memset(nl, 0, sizeof(namelist)); if (strlen(traitname)==0) sprintf(nl->name, "Marker %d",locinumber); else { // remove initial # if any traitname +=strspn(traitname, "# ") ; strncpy(nl->name, traitname, sizeof(nl->name)); } addlist(&markernames, nl); break; case 4 : // Read a quantitative trait break; default: printf("Unknown locus type (%d)\nExiting\n", locus_type); } locinumber++; #ifdef debug printf("Found locus (%s) type %d with %d alleles\n", nl->name, locus_type, num_alleles); #endif } ReadNextNonEmptyLine(); // Now reads the recombination fractions for markers ReadNextNonEmptyLine(); if (nmarkers>1) { distance = vector(1,nmarkers-1); distance[1] = atof(igetstr(buf)); for (i = 2; i<nmarkers; i++) distance[i] = atof(getstr()); } ReadNextNonEmptyLine(); ReadNextNonEmptyLine(); fclose(F); // Fixes order order = ivector(1,nmarkers); invorder = ivector(1,nmarkers); OrderMarkers(tmpbuf); }
/* * The task that is periodically triggered by an interrupt, as described at the * top of this file. */ static void prvISRTriggeredTask( void* pvParameters ); /* * Configures the T5 timer peripheral to generate the interrupts that unblock * the task implemented by the prvISRTriggeredTask() function. */ static void prvSetupT5( void ); /* The timer 5 interrupt handler. As this interrupt uses the FreeRTOS assembly entry point the IPL setting in the following function prototype has no effect. */ void __attribute__( (interrupt(ipl3), vector(_TIMER_5_VECTOR))) vT5InterruptWrapper( void ); /*-----------------------------------------------------------*/ /* The semaphore given by the T5 interrupt to unblock the task implemented by the prvISRTriggeredTask() function. */ static SemaphoreHandle_t xBlockSemaphore = NULL; /*-----------------------------------------------------------*/ void vStartISRTriggeredTask( void ) { /* Create the task described at the top of this file. The timer is configured by the task itself. */ xTaskCreate( prvISRTriggeredTask, /* The function that implements the task. */ "ISRt", /* Text name to help debugging - not used by the kernel. */ configMINIMAL_STACK_SIZE, /* The size of the stack to allocate to the task - defined in words, not bytes. */
vector operator^(vector r){return vector(y*r.z-z*r.y,z*r.x-x*r.z,x*r.y-y*r.x);} //Cross-product
// The main function. It generates a PPM image to stdout. // Usage of the program is hence: ./card > erk.ppm int main(int argc, char **argv) { F(); int w = 512, h = 512; int num_threads = std::thread::hardware_concurrency(); if (num_threads==0) //8 threads is a reasonable assumption if we don't know how many cores there are num_threads=8; if (argc > 1) { w = atoi(argv[1]); } if (argc > 2) { h = atoi(argv[2]); } if (argc > 3) { num_threads = atoi(argv[3]); } printf("P6 %d %d 255 ", w, h); // The PPM Header is issued // The '!' are for normalizing each vectors with ! operator. vector g=!vector(-5.5f,-16,0), // Camera direction a=!(vector(0,0,1)^g)*.002f, // Camera up vector...Seem Z is pointing up :/ WTF ! b=!(g^a)*.002f, // The right vector, obtained via traditional cross-product c=(a+b)*-256+g; // WTF ? See https://news.ycombinator.com/item?id=6425965 for more. int s = 3*w*h; char *bytes = new char[s]; auto lambda=[&](unsigned int seed, int offset, int jump) { for (int y=offset; y<h; y+=jump) { //For each row int k = (h - y - 1) * w * 3; for(int x=w;x--;) { //For each pixel in a line //Reuse the vector class to store not XYZ but a RGB pixel color vector p(13,13,13); // Default pixel color is almost pitch black //Cast 64 rays per pixel (For blur (stochastic sampling) and soft-shadows. for(int r=64;r--;) { // The delta to apply to the origin of the view (For Depth of View blur). vector t=a*(R(seed)-.5f)*99+b*(R(seed)-.5f)*99; // A little bit of delta up/down and left/right // Set the camera focal point vector(17,16,8) and Cast the ray // Accumulate the color returned in the p variable p=S(vector(17,16,8)+t, //Ray Origin !(t*-1+(a*(R(seed)+x)+b*(y+R(seed))+c)*16) // Ray Direction with random deltas // for stochastic sampling , seed)*3.5f+p; // +p for color accumulation } bytes[k++] = (char)p.x; bytes[k++] = (char)p.y; bytes[k++] = (char)p.z; } } }; std::mt19937 rgen; std::vector<std::thread> threads; for(int i=0;i<num_threads;++i) { threads.emplace_back(lambda, rgen(), i, num_threads); } for(auto& t : threads) { t.join(); } fwrite(bytes, 1, s, stdout); delete [] bytes; }
vector operator*(float r){return vector(x*r,y*r,z*r);} //Vector scaling
vector operator+(vector r){return vector(x+r.x,y+r.y,z+r.z);} //Vector add