;+ ;PROCEDURE: mvn_sta_get_c6_co2 ;PURPOSE: ; Returns APID c6 data structure at a single time from common generated by mvn_sta_prod_cal.pro ;INPUT: ; time: dbl time of data to be returned ; ;KEYWORDS: ; start: 0,1 if set, gets first time in common block ; en: 0,1 if set, gets last time in common block ; advance 0,1 if set, gets next time in common block ; retreat 0,1 if set, gets previous time in common block ; index long gets data at the index value "ind" in common block ; calib: 0,1 not working yet, allows alternate calibration ; times 0,1 returns an array of times for all the data, returns 0 if no data ; ; ;CREATED BY: J. McFadden ;VERSION: 1 ;LAST MODIFICATION: 13/11/12 ;MOD HISTORY: ; ;NOTES: ; Data structures can be used as inputs to functions such as n_4d.pro, v_4d.pro ; Or used in conjunction with iterative programs such as get_2dt.pro, get_en_spec.pro ;- FUNCTION mvn_sta_get_c6_co2,time,START=st,EN=en,ADVANCE=adv,RETREAT=ret,index=ind,calib=calib,times=times common mvn_c6,get_ind,all_dat common mvn_sta_c6_co2,co2_valid if n_elements(get_ind) eq 0 then begin if keyword_set(times) then return,0 dat = {project_name:'MAVEN',valid:0} print,' ERROR - mvn c6 data not loaded' return,dat endif else if get_ind eq -1 then begin dat = {project_name:'MAVEN',valid:0} print,' ERROR - mvn c6 data not loaded' return,dat endif else if keyword_set(times) then begin dat=(all_dat.time+all_dat.end_time)/2. return,dat endif else begin if (n_elements(time) eq 0) and (not keyword_set(st)) and (not keyword_set(en)) $ and (not keyword_set(adv)) and (not keyword_set(ret)) and (n_elements(ind) eq 0) $ then ctime,time,npoints=1 if keyword_set(st) then ind=0l $ else if keyword_set(en) then ind=n_elements(all_dat.time)-1 $ else if keyword_set(adv) then ind=get_ind+1 $ else if keyword_set(ret) then ind=get_ind-1 $ else if n_elements(ind) ne 0 then ind=ind $ else tmpmin = min(abs(all_dat.time-time),ind) ; this routine only valid for static mode 1,2,7 at this time ; you can bypass this default for testing by declaring common mvn_sta_c6_co2,co2_valid and setting co2_valid=1 ; energy-anode dependence of ion straggling in carbon foils needed for other modes mode = all_dat.mode[ind] if ind lt 0 or ind ge n_elements(all_dat.time) or not ((mode eq 1) or (mode eq 2) or (mode eq 7) or keyword_set(co2_valid)) then begin dat = {project_name: all_dat.project_name, $ spacecraft: all_dat.spacecraft, $ data_name: all_dat.data_name+' co2', $ apid: all_dat.apid, $ valid: 0} return,dat endif else begin while (all_dat.valid[ind] eq 0 and ind+1 lt n_elements(all_dat.time)) do ind=ind+1 mode = all_dat.mode[ind] rate = all_dat.rate[ind] swp_ind = all_dat.swp_ind[ind] mlut_ind= all_dat.mlut_ind[ind] eff_ind = all_dat.eff_ind[ind] att_ind = all_dat.att_ind[ind] str_element,all_dat,'gf_corr',success=success if success then gf_corr=reform(all_dat.gf_corr[ind,*])#replicate(1.,all_dat.nmass) else gf_corr=1. gf2 = (reform(all_dat.gf[swp_ind,*,att_ind])#replicate(1.,all_dat.nmass))*gf_corr ; gf2 = reform(all_dat.gf[swp_ind,*,att_ind])#replicate(1.,all_dat.nmass) dat = {project_name: all_dat.project_name, $ spacecraft: all_dat.spacecraft, $ data_name: all_dat.data_name+' co2', $ apid: all_dat.apid, $ units_name: 'counts', $ units_procedure: all_dat.units_procedure, $ valid: all_dat.valid[ind], $ quality_flag: all_dat.quality_flag[ind], $ time: all_dat.time[ind], $ end_time: all_dat.end_time[ind], $ delta_t: all_dat.delta_t[ind], $ integ_t: all_dat.integ_t[ind], $ ; eprom_ver: all_dat.eprom_ver[ind], $ ; header: all_dat.header[ind], $ mode: mode, $ rate: rate, $ swp_ind: swp_ind, $ mlut_ind: mlut_ind, $ eff_ind: eff_ind, $ att_ind: att_ind, $ nenergy: all_dat.nenergy, $ energy: reform(all_dat.energy[swp_ind,*,*]), $ denergy: reform(all_dat.denergy[swp_ind,*,*]), $ nbins: all_dat.nbins, $ bins: all_dat.bins, $ ndef: all_dat.ndef, $ nanode: all_dat.nanode, $ theta: reform(all_dat.theta[swp_ind,*,*]), $ dtheta: reform(all_dat.dtheta[swp_ind,*,*]), $ phi: reform(all_dat.phi[swp_ind,*,*]), $ dphi: reform(all_dat.dphi[swp_ind,*,*]), $ domega: reform(all_dat.domega[swp_ind,*,*]), $ gf: gf2, $ eff: reform(all_dat.eff[eff_ind,*,*]), $ geom_factor: all_dat.geom_factor, $ dead1: all_dat.dead1, $ dead2: all_dat.dead2, $ dead3: all_dat.dead3, $ nmass: all_dat.nmass, $ mass: all_dat.mass, $ mass_arr: reform(all_dat.mass_arr[swp_ind,*,*]), $ tof_arr: reform(all_dat.tof_arr[mlut_ind,*,*]), $ twt_arr: reform(all_dat.twt_arr[mlut_ind,*,*]), $ charge: all_dat.charge, $ sc_pot: all_dat.sc_pot[ind], $ magf: reform(all_dat.magf[ind,*]), $ quat_sc: reform(all_dat.quat_sc[ind,*]), $ quat_mso: reform(all_dat.quat_mso[ind,*]), $ bins_sc: reform(all_dat.bins_sc[ind,*]), $ pos_sc_mso: reform(all_dat.pos_sc_mso[ind,*]), $ bkg: reform(all_dat.bkg[ind,*,*]), $ dead: reform(all_dat.dead[ind,*,*]), $ cnts: reform(all_dat.data[ind,*,*]), $ data: reform(all_dat.data[ind,*,*])} get_ind=ind ; remove everything but co2 dat2=dat mass_arr=reform(dat.mass_arr[31,*]) ms3 = 40. ms4 = 60. ; mass_scale=8.0 & cnts_scale=1.05 & ms1=27.0 & ms2=40.0 ; this works best for ram anode to get sc_pot agreement and no flow ; mass_scale=8.0 & cnts_scale=0.66 & ms1=29.2 & ms2=35.6 ; this works best for ram anode to get sc_pot agreement and no flow mass_scale=8.0 & cnts_scale=0.85 & ms1=29.2 & ms2=37.9 ; modified 20170521 ; mass_scale=8.0 & cnts_scale=0.90 & ms1=29.2 & ms2=37.9 ; testing - works better for 20170712 for along-track near zero ; mass_scale=8.0 & cnts_scale=0.80 & ms1=29.2 & ms2=37.9 ; testing - not that good for 201805 co2 mode - .85 still best ; mass_scale=7.5 & cnts_scale=0.70 & ms1=29.2 & ms2=37.9 ; testing 20180922, used nightside O2+ for calibration (very little CO2+) 20180908/0357UT ; mass_scale=7.5 & cnts_scale=0.55 & ms1=29.2 & ms2=37.9 ; testing 20181212, on 20180526 data ind32 = where(mass_arr ge ms1 and mass_arr le ms2,count) ; o2+ straggling changes with time, likely due to thinning of the foils ; this corrects the linear straggling term based on observations on the days listed t0=dat.time t1=time_double('2018-04-24') t2=time_double('2022-09-13') cnts1_scale = 0.90 + 0.15*(t0-t1)/(t2-t1) & cnts2_scale=2000. cnts1 = total(dat.cnts[*,ind32]-dat.bkg[*,ind32],2) cnts0 = total(dat.cnts,2) dead0 = reform(dat.dead[*,0]) ; the non-linear term, or mass peak shift to higher mass with rate, depends on rate squared ; c6 data is averaged over deflectors, so use c8 data product to correct for rate changes with deflection c8 = mvn_sta_get_c8(dat.time) normc8 = reform(c8.cnts*c8.dead)/(.000001+total(reform(c8.cnts*c8.dead),2)#replicate(1.,16)) cnts2 = total(((cnts0#replicate(1.,16))*normc8)*((cnts1#replicate(1.,16))*normc8),2) ; assume similar power law variation of o2+ stragglers for linear and non-linear terms ; bkg1 is the linear straggling term bkg1 = (cnts1#replicate(1.,64)/cnts1_scale)*(dat.mass_arr gt ms3)*exp(-dat.mass_arr/mass_scale)*dat.twt_arr ; bkg2 is the non-linear straggling term bkg2 = (cnts2#replicate(1.,64)/cnts2_scale)*(dat.mass_arr gt ms3)*exp(-dat.mass_arr/mass_scale)*dat.twt_arr ; add all the bkg together dat.bkg = dat.bkg+bkg1+bkg2 ; removal all mass bins outside co2+ mass range mask = (dat.mass_arr gt ms3)*(dat.mass_arr lt ms4) dat.bkg = dat.bkg*mask dat.cnts = dat.cnts*mask ; remove all counts in an energy bin if the total counts in an energy bin is less than zero ind33 = where(total(dat.cnts,2) lt 0.,count) if count ge 1 then dat.cnts[ind33,*]=0. dat.data=dat.cnts ; fix the dat.dead for co2 by adjusting it for differences in efficiency between o2 and co2. ; note that dat.dead tof efficiency was determined for all ions at that energy based on start/stop efficiency ; so dat.dead corrects for the average efficiency with rate (droop, deadtime) but not relative efficiency which depends on mass ; the average efficiency will depend on the dominant ion and relative efficiency variations of minor ions create small errors w/o this correction ; the below code corrects for efficiency variations with a mixture of o2+ and co2+, ignoring other ions by treating them as having same eff as o2+ ; note that dat.eff is the same constant for all ions, since rate dependence of efficiencies (due to mcp droop and deadtime) dominate ; since o2+ dominates at periapsis, this corrects for the relative efficiency of co2+ being different by 1.25 (lower efficiency) mass_arr=reform(dat2.mass_arr(16,*)) ind_o2 = where(mass_arr lt 40.) cnt_o2 = total(dat2.cnts[*,ind_o2],2)>10. ; co2_eff_corr = 1.6 ; ground calibrations indicated this was ~1.6, perhaps foil outgassing increased co2+ penetration co2_eff_corr = 1.25 ; determined from inflight calibration using apid d9 - program plot_d9r.pro - checked several days during mission cnt_co2 = total(dat.data,2)>10. eff_corr = (cnt_o2*co2_eff_corr+cnt_co2)/(cnt_o2+cnt_co2) dat.dead = dat.dead*(eff_corr#replicate(1.,64)) endelse endelse return,dat end