예제 #1
0
void save_dmreal(SIM_T *simu){
    const PARMS_T *parms=simu->parms;
    const RECON_T *recon=simu->recon;
    if(parms->plot.run){
    	for(int idm=0; idm<parms->ndm; idm++){
	    if(simu->dmproj && simu->dmproj->p[idm]){
		drawopd("DM",recon->aloc->p[idm], simu->dmproj->p[idm]->p,NULL,
			"ATM to DM Projection (Hi)","x (m)","y (m)",
			"Proj Hi %d",idm);
	    }
	}
	//2014-05-28: moved from filter.c to here for synchronous display with dmint.
	for(int idm=0; idm<parms->ndm; idm++){
	    if(simu->dmreal && simu->dmreal->p[idm]){
		drawopd("DM", simu->recon->aloc->p[idm], simu->dmreal->p[idm]->p,NULL,
			"Actual DM Actuator Position","x (m)", "y (m)", "Real %d",idm);
	    }
	}
    }
    if(parms->save.dm){
	zfarr_dcell(simu->save->dmreal, simu->isim, simu->dmreal);
	zfarr_dcell(simu->save->dmcmd, simu->isim, simu->dmcmd);
	if(simu->ttmreal){
	    simu->save->ttmreal->p[simu->isim*2]=simu->ttmreal->p[0];
	    simu->save->ttmreal->p[simu->isim*2+1]=simu->ttmreal->p[1];
	}
    }
}
예제 #2
0
void maos_isim(int isim){
    const PARMS_T *parms=global->parms;
    RECON_T *recon=global->recon;
    SIM_T   *simu =global->simu;
    int iseed=global->iseed;
    int simstart=parms->sim.start;
    int simend=parms->sim.end;
    if(isim==simstart+1){//skip slow first step.
	tk_atm=myclockd();
    }
    if(isim+2+parms->sim.dtrat_hi>=simend){
	draw_single=0;
    }
    double ck_0=myclockd();
    simu->isim=isim;
    simu->status->isim=isim;
    sim_update_etf(simu);
    if(parms->atm.frozenflow){
#if USE_CUDA
	if(parms->gpu.evl || parms->gpu.wfs){
	    /*may need to copy another part */
	    gpu_atm2gpu(simu->atm, simu->atmscale, parms, iseed, isim);
	}
#endif
    }else{
	//Do not put this one inside parallel 
	genatm(simu);
	/*re-seed the atmosphere in case atm is loaded from shm/file */
	seed_rand(simu->atm_rand, lrand(simu->init_rand));
    }
    OMPTASK_SINGLE{
	if(parms->sim.dmproj){
	    /* teporarily disable FR.M so that Mfun is used.*/
	    cell *FRM=recon->FR.M; recon->FR.M=NULL; 
	    muv_solve(&simu->dmproj, &recon->FL, &recon->FR, NULL);
	    recon->FR.M=FRM;/*set FR.M back*/
	    if(parms->save.dm){
		zfarr_dcell(simu->save->dmproj, simu->isim, simu->dmproj);
	    }
	    if(!parms->fit.square){
		/* Embed DM commands to a square array for fast ray tracing */
		for(int idm=0; idm<parms->ndm; idm++){
		    loc_embed(simu->dmprojsq->p[idm], recon->aloc->p[idm], simu->dmproj->p[idm]->p);
		}
	    }
#if USE_CUDA
	    if(parms->gpu.evl || parms->gpu.wfs){
		gpu_dmproj2gpu(simu->dmprojsq);
	    }
#endif
	}
	save_dmreal(simu);
	extern int NO_RECON, NO_WFS, NO_EVL;
	if(PARALLEL){
	    /*
	      We do the big loop in parallel to make better use the
	      CPUs. Notice that the reconstructor is working on grad from
	      last time step so that there is no confliction in data access.
	    */
	    /*when we want to apply idealngs correction, wfsgrad need to wait for perfevl. */
	    long group=0;
	    if(parms->gpu.evl && !NO_EVL){
		//Queue tasks on GPU, no stream sync is done
		QUEUE_THREAD(group, simu->perf_evl_pre, 0);
	    }
	    if(!parms->tomo.ahst_idealngs && parms->gpu.wfs && !NO_WFS){
		//task for each wfs
		QUEUE_THREAD(group, simu->wfs_grad_pre, 0);
	    }
	    if(!NO_RECON){
		//don't put this first. It has cpu overhead in computing gradol
		QUEUE(group, reconstruct, simu, 1, 0);
	    }
	    if(!NO_EVL){
		if(parms->gpu.evl){
		    //wait for GPU tasks to be queued before calling sync
		    WAIT(group);
		}
		QUEUE(group, perfevl, simu, 1, 0);
	    }
	    if(!NO_WFS){
		if(parms->tomo.ahst_idealngs || (parms->gpu.wfs && !parms->gpu.evl)){
		    //in ahst_idealngs mode, weight for perfevl to finish.
		    //otherwise, wait for GPU tasks to be queued before calling sync
		    WAIT(group);
		}
		QUEUE(group, wfsgrad, simu, 1, 0);
	    }
	    if(!NO_RECON){
		//wait for all tasks to finish before modifying dmreal
		WAIT(group);
		shift_grad(simu);/*before filter() */
		filter_dm(simu);/*updates dmreal, so has to be after prefevl/wfsgrad is done. */
	    }
	    WAIT(group);
	}else{/*do the big loop in serial mode. */
	    if(parms->sim.closeloop){
		if(!NO_EVL) perfevl(simu);/*before wfsgrad so we can apply ideal NGS modes */
		if(!NO_WFS) wfsgrad(simu);/*output grads to gradcl, gradol */
		if(!NO_RECON) {
		    reconstruct(simu);/*uses grads from gradlast cl, gradlast ol. */
		    shift_grad(simu);
		    filter_dm(simu);
		}
	    }else{/*in OL mode,  */
		if(!NO_WFS) wfsgrad(simu);
		if(!NO_RECON) {
		    shift_grad(simu);
		    reconstruct(simu);
		    filter_dm(simu);
		}
		if(!NO_EVL) perfevl(simu);
	    }
	}
    }
    double ck_end=myclockd();
    long steps_done=iseed*(simend-simstart)+(isim+1-simstart);
    long steps_rest=parms->sim.nseed*(simend-simstart)-steps_done;
    if(isim!=simstart){
	simu->status->rest=(long)((ck_end-tk_0-(tk_atm-tk_1)*(iseed+1))/steps_done*steps_rest
				  +(tk_atm-tk_1)*(parms->sim.nseed-iseed-1));
	simu->status->mean=(ck_end-tk_atm)/(double)(isim-simstart);
    }
    simu->status->laps=(long)(ck_end-tk_0);
    simu->status->tot  =ck_end-ck_0;
    simu->status->wfs  =simu->tk_wfs;
    simu->status->recon=simu->tk_recon;
    simu->status->other=simu->tk_cache;
    simu->status->eval =simu->tk_eval;
    simu->status->scale=1;
    if(simu->timing){
	simu->timing->p[isim*simu->timing->nx]=get_job_mem();
	simu->timing->p[isim*simu->timing->nx+1]=simu->status->tot;
	simu->timing->p[isim*simu->timing->nx+2]=simu->status->wfs;
	simu->timing->p[isim*simu->timing->nx+3]=simu->status->recon;
	simu->timing->p[isim*simu->timing->nx+4]=simu->status->eval;
    }
    double this_time=myclockd();
    if(this_time>simu->last_report_time+1 || isim+1==simend || parms->sim.pause){
	/*we don't print out or report too frequently. */
	simu->last_report_time=this_time;
#if defined(__linux__) || defined(__APPLE__)
	scheduler_report(simu->status);
#endif
	print_progress(simu);
    }
}
예제 #3
0
void save_recon(SIM_T *simu){
    const PARMS_T *parms=simu->parms;
    const RECON_T *recon=simu->recon;
    if(parms->plot.run){
	if(parms->recon.alg==0){
	    for(int i=0; simu->opdr && i<simu->opdr->nx; i++){
		if(simu->opdr->p[i]){
		    drawopd("opdr", recon->xloc->p[i], simu->opdr->p[i]->p, NULL,
			    "Reconstructed Atmosphere","x (m)","y (m)","opdr %d",i);
		}
	    }
	    for(int i=0; simu->dmfit && i<simu->dmfit->nx; i++){
		if(simu->dmfit->p[i]){
		    drawopd("DM", recon->aloc->p[i], simu->dmfit->p[i]->p,NULL,
			    "DM Fitting Output","x (m)", "y (m)","Fit %d",i);
		}
	    }
	}
	if(!parms->recon.modal){
	    for(int idm=0; simu->dmerr && idm<parms->ndm; idm++){
		if(simu->dmerr->p[idm]){
		    drawopd("DM",recon->aloc->p[idm], simu->dmerr->p[idm]->p,NULL,
			    "DM Error Signal (Hi)","x (m)","y (m)",
			    "Err Hi %d",idm);
		}
	    }
	}
	for(int idm=0; simu->dmerr && idm<parms->ndm; idm++){
	    if(simu->dmint->mint->p[0]->p[idm]){
		drawopd("DM",recon->aloc->p[idm], simu->dmint->mint->p[0]->p[idm]->p,NULL,
			"DM Integrator (Hi)","x (m)","y (m)",
			"Int Hi %d",idm);
	    }
	}
	if(simu->dm_wfs){
	    for(int iwfs=0; iwfs<parms->nwfs; iwfs++){
		int ipowfs=parms->wfs[iwfs].powfs;
		int imoao=parms->powfs[ipowfs].moao;
		if(imoao<0) continue;
		drawopd("moao", recon->moao[imoao].aloc->p[0], simu->dm_wfs->p[iwfs]->p, NULL,
			"MOAO", "x(m)", "y(m)", "WFS %d", iwfs);
	    }
	}
	if(simu->dm_evl){
	    int imoao=parms->evl.moao;
	    for(int ievl=0; ievl<parms->evl.nevl && imoao>=0; ievl++){
		drawopd("moao", recon->moao[imoao].aloc->p[0], simu->dm_evl->p[ievl]->p, NULL,
			"MOAO", "x(m)", "y(m)", "Evl %d", ievl);
	    }
	}
    }
    if(parms->plot.run && simu->Merr_lo){
	dcell *dmlo=NULL;
	switch(simu->parms->recon.split){
	case 1:
	    ngsmod2dm(&dmlo, recon, simu->Merr_lo, 1);
	    break;
	case 2:
	    dcellmm(&dmlo, simu->recon->MVModes, simu->Merr_lo, "nn", 1);
	    break;
	}
	for(int idm=0; dmlo && idm<parms->ndm; idm++){
	    drawopd("DM",recon->aloc->p[idm], dmlo->p[idm]->p,NULL,
		    "DM Error Signal (Lo)","x (m)","y (m)",
		    "Err Lo %d",idm);
	}
	dcellfree(dmlo);
    }
    if(parms->plot.run && simu->Mint_lo && simu->Mint_lo->mint->p[0]){
	dcell *dmlo=NULL;
	switch(simu->parms->recon.split){
	case 1:
	    ngsmod2dm(&dmlo, recon, simu->Mint_lo->mint->p[0], 1);
	    break;
	case 2:
	    dcellmm(&dmlo, simu->recon->MVModes, simu->Mint_lo->mint->p[0], "nn", 1);
	    break;
	}
	for(int idm=0; dmlo && idm<parms->ndm; idm++){
	    drawopd("DM",recon->aloc->p[idm], dmlo->p[idm]->p,NULL,
		    "DM Integrator (Lo)","x (m)","y (m)",
		    "Int Lo %d",idm);
	}
	dcellfree(dmlo);
    }
    if(parms->recon.alg==0){/*minimum variance tomo/fit reconstructor */
	if(parms->save.opdr){
	    zfarr_dcell(simu->save->opdr, simu->reconisim, simu->opdr);
	}
	if(parms->save.opdx || parms->plot.opdx){
	    dcell *opdx=simu->opdx;
	    if(!opdx){
		atm2xloc(&opdx, simu);
	    }
	    if(parms->save.opdx){
		zfarr_dcell(simu->save->opdx, simu->isim, opdx);
	    }
	    if(parms->plot.opdx){ /*draw opdx */
		for(int i=0; i<opdx->nx; i++){
		    if(opdx->p[i]){
			drawopd("opdx", recon->xloc->p[i], opdx->p[i]->p, NULL,
				"Atmosphere Projected to XLOC","x (m)","y (m)","opdx %d",i);
		    }
		}
	    }
	    if(!parms->sim.idealfit){
		dcellfree(opdx);
	    }
	}
    }
    if(parms->save.dm && (!parms->sim.closeloop || simu->isim>0)){
	if(simu->dmfit){
	    zfarr_dcell(simu->save->dmfit, simu->reconisim, simu->dmfit);
	}
	if(simu->dmerr){
	    zfarr_dcell(simu->save->dmerr, simu->reconisim, simu->dmerr);
	}
	if(simu->dmint->mint->p[0]){
	    zfarr_dcell(simu->save->dmint, simu->reconisim, simu->dmint->mint->p[0]);
	}
	if(simu->Merr_lo){
	    zfarr_dcell(simu->save->Merr_lo, simu->reconisim, simu->Merr_lo);
	    if(!parms->sim.fuseint && simu->Mint_lo->mint->p[0]){
		zfarr_dcell(simu->save->Mint_lo, simu->reconisim, simu->Mint_lo->mint->p[0]);
	    }
	}
    }
    const int seed=simu->seed;
    if(parms->save.ngcov>0 && CHECK_SAVE(parms->sim.start, parms->sim.end-(parms->sim.closeloop?1:0), simu->reconisim, parms->save.gcovp)){
	double scale=1./(double)(simu->reconisim-parms->sim.start+1);
	dcellscale(simu->gcov, scale);
	for(int igcov=0; igcov<parms->save.ngcov; igcov++){
	    writebin(simu->gcov->p[igcov], "gcov_%d_wfs%ld_%ld_%d.bin", seed,
		   parms->save.gcov->p[igcov*2], parms->save.gcov->p[igcov*2+1],
		   simu->reconisim+1);
	}
	dcellscale(simu->gcov, 1./scale); //2016-06-07: Do not reset.
    }
    if(parms->sim.psfr && CHECK_SAVE(parms->evl.psfisim, parms->sim.end-(parms->sim.closeloop?1:0), simu->reconisim, parms->sim.psfr)){
	info2("Output PSF Recon Telemetry\n");
	long nstep=simu->reconisim+1-parms->evl.psfisim;
	double scale=1./nstep;
	dcellscale(simu->ecov, scale);
	if(!parms->dbg.useopdr || parms->sim.idealfit){
	    writebin(simu->ecov, "ecov_%d_%d", seed, simu->reconisim);
	}else{/*deprecated */
	    char strht[24];
	    for(int ievl=0; ievl<parms->evl.nevl; ievl++){
		if(!simu->ecov->p[ievl]) continue;
		if(isfinite(parms->evl.hs->p[ievl])){
		    snprintf(strht, 24, "_%g", parms->evl.hs->p[ievl]);
		}else{
		    strht[0]='\0';
		}
		writebin(simu->ecov->p[ievl], "ecov_%d_x%g_y%g%s_%d.bin", seed, 
		       parms->evl.thetax->p[ievl]*206265,
		       parms->evl.thetay->p[ievl]*206265, strht, simu->reconisim);
	    }
	}
	dcellscale(simu->ecov, 1./scale); //2016-06-07: Do not reset. 
    }
}