
;function sot_fix_pointing_fixed_20211221, index, t0=t0, t1=t1, files=files, oindex=oindex, sp_flag=sp_flag, $
function sot_fix_pointing, index, t0=t0, t1=t1, files=files, oindex=oindex, sp_flag=sp_flag, $
  use_shimizu=use_shimizu, $
  dir_corr_db=dir_corr_db, corr_db=corr_db, do_corr_db_update=do_corr_db_update, $
  dt_sec_corr_prior_max=dt_sec_corr_prior_max, dt_sec_corr_after_max=dt_sec_corr_after_max, $
  initialize=initialize, do_write=do_write, $
  verbose=verbose, qstop=qstop, _extra=_extra

;+
; History:
;   2017-06-02 - GLS - Completely re-written.
;   2020-07-28 - GLS - Added checks to insure a valid corr_db record is used
;   2020-08-11 - GLS - ??
;   2020-12-17 - GLS - Change file path references from hard-coded local paths to $SSWDB paths
;   2021-12-21 - GLS - Added time limits for applying synoptic image database correctiuon
;-

; Program name and version:
prognam = 'SOT_FIX_POINING.PRO'
progver = 'V1.1'
prog_nam_ver = 'SOT_FIX_POINING.PRO V1.1'

corr_db_ver = ''

if not exist(dt_sec_corr_prior_max) then dt_sec_corr_prior_max = 3600d0
if not exist(dt_sec_corr_after_max) then dt_sec_corr_after_max = 3600d0

if not keyword_set(verbose) then verbose = 0
quiet = 1 - verbose
if not keyword_set(quiet_where) then quiet_where = 1

; Check for corr_db passed and if no corr_db overlap:
if ~exist(corr_db) then begin
   corr_db_not_passed = 1
endif else begin
  if size(corr_db, /type) ne 8 then corr_db_no_overlap = 1
endelse

; Define corr_db directory if not passed in:
if ~exist(dir_corr_db) then dir_corr_db = '$SSWDB/hinode/gen/sot_corr_db_corrected'
; dir_corr_db = '/net/topaz/Users/slater/data/sot_corr_db_corrected_1'

; Create corr_db directory if it does not exist:
; mk_dir, dir_corr_db

; Create working index array for updated index headers if it does not exist:

delvarx, index_arr
if not exist(index) then begin
   if not keyword_set(sp_flag) then begin
      mreadfits_header, files, index_arr
   endif else begin
      n_files = n_elements(files)
      for i=0, n_files-1 do begin
         read_sotsp, files[i], index0
         if not exist(index_arr) then index_arr = index0 else $
            index_arr = concat_struct(index_arr, index0)
      endfor
   endelse
endif else begin
   index_arr = index
endelse
index = index_arr
oindex = index_arr

; Define time and orignial pointing tag arrays from the index_arr:
n_img = n_elements(index_arr)
t_img = index_arr.date_obs

t_img_sec = anytim(t_img)
xcen_orig = index_arr.xcen
ycen_orig = index_arr.ycen

; Initialize xcen, ycen arrays (to be used later to update index_arr values):
xcen = xcen_orig
ycen = ycen_orig

; Initialize corr_db-related parameters (for use in tag definitions later)"
xcen_shi           = dblarr(n_img) - 99999d0
ycen_shi           = dblarr(n_img) - 99999d0
xcen_syn           = dblarr(n_img) - 99999d0
ycen_syn           = dblarr(n_img) - 99999d0
xcen_cdb           = dblarr(n_img) - 99999d0
ycen_cdb           = dblarr(n_img) - 99999d0

peak_str           = dblarr(n_img) - 99999d0
xdisp_rot          = dblarr(n_img) - 99999d0
ydisp_rot          = dblarr(n_img) - 99999d0
xdisp_tot          = dblarr(n_img) - 99999d0
ydisp_tot          = dblarr(n_img) - 99999d0
xdisp              = dblarr(n_img) - 99999d0
ydisp              = dblarr(n_img) - 99999d0
file_sot           = strarr(n_img)
file_sdo           = strarr(n_img)
t_sot              = strarr(n_img)
t_sdo              = strarr(n_img)
dt_sdo             = dblarr(n_img) - 99999d0
;qual_sdo          = dblarr(n_img) - 99999d0
ref_file_sot       = strarr(n_img)
ref_time_sot       = strarr(n_img)

dt_sec_reset_prior = lonarr(n_img) - 99999l
dt_sec_reset_after = lonarr(n_img) - 99999l
dt_sec_corr_prior  = lonarr(n_img) - 99999l
dt_sec_corr_after  = lonarr(n_img) - 99999l
ss_corr_prior      = lonarr(n_img) - 99999l
ss_corr_after      = lonarr(n_img) - 99999l
corr_switch        = lonarr(n_img) - 99999l

; ********************************************************************
; Default is to use the Shimizu offsets from Toshi Shimizu's database,
; which covers the entire SOT FG archive:
; ********************************************************************

shimizu_offsets = get_shimizu(index_arr.date_obs)

xcen_correction_shimizu = reform(shimizu_offsets[0,*])
ycen_correction_shimizu = reform(shimizu_offsets[1,*])
xcen_shimizu = xcen_orig + xcen_correction_shimizu
ycen_shimizu = ycen_orig + ycen_correction_shimizu

; Update xcen, ycen arrays with first correction (Shimizu):
xcen = xcen_shimizu
ycen = ycen_shimizu

HELP, xcen_shimizu, ycen_shimizu ; & STOP

;PRINT, xcen_orig, xcen_correction_shimizu, xcen_shimizu, ycen_orig, ycen_correction_shimizu, ycen_shimizu
; ******************************************************************
; We now have default correction values from the Shimizu database in
; case there are no appropriate corr_db values.
; ******************************************************************

; *********************************************************************
; SECTION 1: Optionally update the corr_db database using Ted Tarbell's
;            analysis of the SOT FG synoptic image database:
; *********************************************************************

if keyword_set(do_corr_db_update) then begin

   if not exist(corr_db) then begin
      print, 'Restoring uncorrected SOT correlation database.'
      restore, '$SSWDB/hinode/gen/corr_db_mission.sav'
;     restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/corr_db_mission.sav'

      date_obs_corr_db = corr_db_mission.date_obs
      t_obs_sec_corr_db = anytim(date_obs_corr_db)
      ss_uniq = UNIQ(t_obs_sec_corr_db, SORT(t_obs_sec_corr_db))
      corr_db_uniq = corr_db_mission[ss_uniq]
      help, corr_db_uniq

      corr_db = corr_db_uniq
   endif

   date_obs_corr_db = corr_db.date_obs
   t_obs_sec_corr_db = anytim(date_obs_corr_db)
;HELP, corr_db, do_corr_db_update, corr_db_no_overlap, corr_db_not_passed
;STOP, ' Stopping in optional corr_db update code block.'
   peak_str_corr_db = corr_db.peak_str
   xdisp_corr_db = corr_db.xdisp
   ydisp_corr_db = corr_db.ydisp
   xdisp_tot_corr_db = corr_db.xdisp_tot
   ydisp_tot_corr_db = corr_db.ydisp_tot
   xcen_corr = corr_db.xcen
   ycen_corr = corr_db.ycen
   ctmex_corr = corr_db.ctmex
   ctmey_corr = corr_db.ctmey

   t_corr_sec = t_obs_sec_corr_db

; ***************************************************
; Subsection 1.1: Ted's analysis of bad corr results:
; ***************************************************

; Recover original (level0) xcen, ycen offsets:
   xcen0 = xcen_corr - xdisp_tot_corr_db
   ycen0 = ycen_corr - ydisp_tot_corr_db

; Don't use Shimizu offsets:
;  sot_offsets = get_shimizu(corr_db.date_obs)

; ...But instead, use synoptic-derived version of SOT offsets (replacing Shimizu offsets):
   restore, '/$SSWDB/hinode/gen/SOT_x_y_offsets_from_all_synoptics.sav'
;  restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/SOT_x_y_offsets_from_all_synoptics.sav'

; Synoptic offset save file provides 'syn_xdisp_tot_smooth', 'syn_ydisp_tot_smooth',
;   'syn_date_obs'.  Interpolate on these for all corr db records:
   sotx_interp = interpol(syn_xdisp_tot_smooth, anytim(syn_date_obs), t_obs_sec_corr_db)
   soty_interp = interpol(syn_ydisp_tot_smooth, anytim(syn_date_obs), t_obs_sec_corr_db)

   residx0 = xdisp_tot_corr_db - sotx_interp
   residy0 = ydisp_tot_corr_db - soty_interp

; Correction for Hinode roll angle error:
   restore, '/$SSWDB/hinode/gen/HOP79_NS_angles_fit.sav'
;  restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/HOP79_NS_angles_fit.sav'

   nsfit_interp = interpol(nsfit, anytim(fittimes), t_obs_sec_corr_db)

   residx1 = residx0 + ycen0*(nsfit_interp/!radeg)
   residy1 = residy0 - xcen0*(nsfit_interp/!radeg)

; Tilt mirror offsets (also include jitter & orbital wobble)
; Cal coeffs mean of all non-eclipse seasons, 2010-16
   residx = residx1+ctmex_corr/2000.
   residy = residy1+ctmey_corr/2000.

   rdisp  = sqrt(residx^2 +residy^2)

   help, peak_str, rdisp
;  hist_arr  = hist_2d(peak_str, rdisp)

; Filter for bad ones:
   ss_bad = where( (rdisp gt  8. and peak_str lt 6.) or $
                (rdisp gt 14. and peak_str ge 6.) , n_bad)

   print,'Bad ones, r>8 and Pk<6 or r>14 and Pk>6 ', n_bad, ' of ', n_elements(rdisp)

; Correct the bad ones:
   xcen_corr_mission = xcen_corr
   ycen_corr_mission = ycen_corr

   if (n_bad gt 0) then begin
      xdisp_tot_corr_db(ss_bad) = sotx_interp(ss_bad) - xcen0(ss_bad)*(nsfit_interp(ss_bad)/!radeg)
      ydisp_tot_corr_db(ss_bad) = soty_interp(ss_bad) + ycen0(ss_bad)*(nsfit_interp(ss_bad)/!radeg)
      xcen_corr_mission(ss_bad) = xcen0(ss_bad) + xdisp_tot_corr_db(ss_bad)
      ycen_corr_mission(ss_bad) = ycen0(ss_bad) + ydisp_tot_corr_db(ss_bad)
   end

   corr_db.xcen = xcen_corr_mission
   corr_db.ycen = ycen_corr_mission

; Now generate a corrected correlation database:

   sttim_db = anytim(min(t_obs_sec_corr_db), /ccsds, /date)
   entim_db = anytim(max(t_obs_sec_corr_db) + 86400l, /ccsds, /date)

   t_grid = anytim(timegrid(sttim_db, entim_db, days=1), /ccsds)
   t_grid_sec = anytim(t_grid)
   n_grid = n_elements(t_grid)

   for i=0, n_grid-2 do begin
      ss_include = where( ((t_corr_sec ge t_grid_sec[i]) and (t_corr_sec lt t_grid_sec[i+1])), n_include)

      if n_include gt 0 then begin

         geny = 1 & day_round = 1 & nelements = 1 & prefix = 'sot_corr_db_' ; & weeksub = 1
         write_genxcat, corr_db[ss_include], topdir=dir_corr_db, weeksub=weeksub, $
                        prefix=prefix, day_round=day_round, nelements=nelements, $
                        geny=geny, _extra=_extra
;                       prefix=prefix, text=text, catname=catname, $
;                       day_round=day_round, hour_round=hour_round, $
;                       nelements=nelements, delete_time=delete_time, $
;                       no_delete_time=no_delete_time, geny=geny, _extra=_extra
         if (i mod 14) eq 0 then $
            print, ' Finished writing genx catalog file for ' + $
                   anytim(corr_db[ss_include[0]].date_obs, /ccsds, /date)
         
      endif
   endfor

endif

; **********************************************************************
; End SECTION 1: Optional generation of corrected db_corr database using
;                Tarbell synoptic database analysis
; **********************************************************************

; **********************************************************************************
; SECTION 2: Generate improved pointing offsets for each image using the synoptic
;            image database as analyzed by Ted Tarbell, unless the corr_db parameter
;            was passed in with value '-1', which indicates no overlap of corr_db
;            record times with index_arr date_obs times:
; **********************************************************************************

if ~keyword_set(corr_db_no_overlap) then begin

; Restore synoptic-based offsets for all images:
   if not exist(syn_xdisp_tot_smooth) then $
      restore, '$SSWDB/hinode/gen/SOT_x_y_offsets_from_all_synoptics.sav'
;     restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/SOT_x_y_offsets_from_all_synoptics.sav'

   dt_sec_syn_prior_max = 86400l
   dt_sec_syn_after_max = 86400l
   syn_t_sec = anytim(syn_date_obs)
   min_syn_t_sec = min(syn_t_sec) - dt_sec_syn_prior_max
   max_syn_t_sec = max(syn_t_sec) + dt_sec_syn_after_max
   
   ss_syn_ok = where( ((t_img_sec gt min_syn_t_sec) and (t_img_sec lt max_syn_t_sec)), n_syn_ok)

   if n_syn_ok gt 0 then begin

; Synoptic offset save file provides 'syn_xdisp_tot_smooth', 'syn_ydisp_tot_smooth',
;   'syn_date_obs'.  Interpolate on these for all images:
      sot_syn_x_off_interp = interpol(syn_xdisp_tot_smooth, anytim(syn_date_obs), t_img_sec)
      sot_syn_y_off_interp = interpol(syn_ydisp_tot_smooth, anytim(syn_date_obs), t_img_sec)

; Add synoptic-derived corrections to xcen, ycen:
      xcen_syn = xcen_orig + sot_syn_x_off_interp
      ycen_syn = ycen_orig + sot_syn_y_off_interp

; Restore roll correction data:
      if not exist(nsfit) then $
         restore, '$SSWDB/hinode/gen/HOP79_NS_angles_fit.sav'
;        restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/HOP79_NS_angles_fit.sav'

; Interpolate:
      nsfit_interp = interpol(nsfit, anytim(fittimes), t_img_sec)

; Now add correction for Hinode roll angle error to synoptic-corrected xcen, ycen:
      xcen_syn_roll = xcen_syn + ycen_syn*(nsfit_interp/!radeg)
      ycen_syn_roll = ycen_syn - xcen_syn*(nsfit_interp/!radeg)

; Update xcen, ycen arrays with second correction (Tarbell):
      xcen[ss_syn_ok] = xcen_syn_roll[ss_syn_ok]
      ycen[ss_syn_ok] = ycen_syn_roll[ss_syn_ok]

   endif

endif

HELP, xcen, ycen, xcen_syn_roll, ycen_syn_roll, ss_syn_ok ; & STOP

; **************************************************************************************
; SECOND (IMPROVED) ESTIMATE of pointing corrections ( [xcen_syn_roll, ycen_syn_roll] ),
; COMPLETED based upon the synoptic image database analysis.
; **************************************************************************************

; ********************************************************************************
; Finally, check for 'close-in-time' records in the corr_db database to generate a
; further improvement to the pointing correction, unless corr_db_no_overlap
; parameter equals 1
; ********************************************************************************

if ~keyword_set(corr_db_no_overlap) then begin

; If the corr_db database was not passed, then read the relevant records for
; the interval covered by the input index_arr headers, from the database directory:

   if keyword_set(corr_db_not_passed) then begin
      t_db_min = anytim(min(t_img_sec) - long(dt_sec_corr_prior_max), /ccsds)
      t_db_max = anytim(max(t_img_sec) + long(dt_sec_corr_after_max), /ccsds)
;STOP, ' Stopping before read_genxcat of corr_db.'
      read_genxcat, t_db_min, t_db_max, corr_db, topdir=dir_corr_db, $ ; topdir_genx_corrected, $
                    count=count, status=status, initialize=initialize
;HELP, corr_db
   endif

; Do a first-pass filter on 'peak_str' to remove poor cross-correlation results:
   peak_str_corr_db = corr_db.peak_str
   xdisp_tot_corr_db = corr_db.xdisp_tot
   ydisp_tot_corr_db = corr_db.ydisp_tot

; Here we put include a somewhat arbitrary limit
; on the total allowed pointing correction in either axis, in arcsec:
   ss_good = where( (peak_str_corr_db ge 6) and (peak_str_corr_db le 30) and $
                    (abs(xdisp_tot_corr_db) le 20) and (abs(ydisp_tot_corr_db) le 20), n_good)

if n_good ge 1 then begin

   date_obs_corr_db = corr_db.date_obs
   t_obs_sec_corr_db = anytim(date_obs_corr_db)
;HELP, corr_db, do_corr_db_update, corr_db_no_overlap, corr_db_not_passed
;STOP, ' Stopping in "close-in-time" corr_db pointing adjustment block.'
   peak_str_corr_db = corr_db.peak_str
   xdisp_corr_db = corr_db.xdisp
   ydisp_corr_db = corr_db.ydisp
   xdisp_tot_corr_db = corr_db.xdisp_tot
   ydisp_tot_corr_db = corr_db.ydisp_tot
   xcen_corr = corr_db.xcen
   ycen_corr = corr_db.ycen
   ctmex_corr = corr_db.ctmex
   ctmey_corr = corr_db.ctmey

   t_corr_sec = t_obs_sec_corr_db

; Read CT reset database:
   restore, '$SSWDB/hinode/gen/ct_reset_log.sav'
;  restore, '/net/topaz/Users/slater/soft/idl_temp/idl_startup/sot/ct_reset_log.sav'
   t_reset = t_event
   t_reset_sec = anytim(t_reset)
   if keyword_set(qstop) then $
      stop, ' Stopping after CT reset database read in sot_fix_pointing.'

; Loop through image headers (index_arr), calculating corr_db-based pointing
; corrections and updating the pointing parameters:

   for i=0, n_img-1 do begin
      index0 = index_arr[i]

;  ss_already = get_history(index0, caller='SOT_FIX_POINTING', found=found)




      dt_sec_reset_arr = t_img_sec[i] - t_reset_sec
      dt_sec_reset_prior_arr = dt_sec_reset_arr[where(dt_sec_reset_arr ge 0, n_reset_prior)]
      dt_sec_reset_after_arr = dt_sec_reset_arr[where(dt_sec_reset_arr lt 0, n_reset_after)]
      if n_reset_prior gt 0 then $
         dt_sec_reset_prior[i] = min(abs(dt_sec_reset_prior_arr))
      if n_reset_after gt 0 then $
         dt_sec_reset_after[i] = min(abs(dt_sec_reset_after_arr))

      dt_sec_corr_arr = t_img_sec[i] - t_corr_sec
      dt_sec_corr_prior_arr = dt_sec_corr_arr[where(dt_sec_corr_arr ge 0, n_corr_prior)]
      dt_sec_corr_after_arr = dt_sec_corr_arr[where(dt_sec_corr_arr lt 0, n_corr_after)]
      if n_corr_prior gt 0 then begin
         dt_sec_corr_prior[i] = min(abs(dt_sec_corr_prior_arr), ss_corr_prior_min)
         ss_corr_prior[i] = ss_corr_prior_min
      endif
      if n_corr_after gt 0 then begin
         dt_sec_corr_after[i] = min(abs(dt_sec_corr_after_arr), ss_corr_after_min)
         ss_corr_after[i] = ss_corr_after_min
      endif

; Update values for header tag arrays, in cases where the correlation database is to be used:

; The logic here is to try to use nearest prior corr_db record.  If no acceptable prior record
; is found, try to use nearest after corr_db record.
;STOP, 'Stopping in corr_db update logic.'
; Check if dt_sec_corr_prior has been given a non-default (-99999) value:
      if (dt_sec_corr_prior[i] ge 0) then begin

         if ((dt_sec_corr_prior[i] lt dt_sec_corr_prior_max) and $
             (dt_sec_corr_prior[i] lt dt_sec_reset_prior[i])) then begin ; and $
;            (sqrt(xcen_syn[i]*xcen_syn[i] + ycen_syn[i]*ycen_syn[i]) lt 800d0)) then begin
            xcen_cdb[i]  = corr_db[ss_corr_prior[i]].xcen
            ycen_cdb[i]  = corr_db[ss_corr_prior[i]].ycen
            xcen[i]      = corr_db[ss_corr_prior[i]].xcen
            ycen[i]      = corr_db[ss_corr_prior[i]].ycen
;HELP, corr_db, do_corr_db_update, corr_db_no_overlap, corr_db_not_passed
;STOP, ' Stopping in corrdb update code for "dt_sec_corr_prior[i] gt 0".'
            peak_str[i]  = corr_db[ss_corr_prior[i]].peak_str
            xdisp_rot[i] = corr_db[ss_corr_prior[i]].xdisp_rot
            ydisp_rot[i] = corr_db[ss_corr_prior[i]].ydisp_rot
            xdisp_tot[i] = corr_db[ss_corr_prior[i]].xdisp_tot
            ydisp_tot[i] = corr_db[ss_corr_prior[i]].ydisp_tot
            xdisp[i]     = corr_db[ss_corr_prior[i]].ydisp
            ydisp[i]     = corr_db[ss_corr_prior[i]].xdisp
            file_sot[i]  = corr_db[ss_corr_prior[i]].file_sot
            file_sdo[i]  = corr_db[ss_corr_prior[i]].file_sdo
            t_sot[i]     = corr_db[ss_corr_prior[i]].t_sot
            t_sdo[i]     = corr_db[ss_corr_prior[i]].t_sdo
            dt_sdo[i]    = corr_db[ss_corr_prior[i]].dt_sdo
;           qual_sdo[i]  = corr_db[ss_corr_prior[i]].qual_sdo

         endif else begin

; Check if dt_sec_corr_after has been given a non-default (-99999) value:
            if (dt_sec_corr_after[i] ge 0) then begin

               if ((dt_sec_corr_after[i] lt dt_sec_corr_after_max) and $
                   (dt_sec_corr_after[i] lt dt_sec_reset_after[i])) then begin ; and $
;                  (sqrt(xcen_syn[i]*xcen_syn[i] + ycen_syn[i]*ycen_syn[i]) lt 800d0)) then begin
                  xcen[i]      = corr_db[ss_corr_after[i]].xcen
                  ycen[i]      = corr_db[ss_corr_after[i]].ycen
;HELP, corr_db, do_corr_db_update, corr_db_no_overlap, corr_db_not_passed
;STOP, ' Stopping in corrdb update code for "dt_sec_corr_after[i] gt 0".'
                  peak_str[i]  = corr_db[ss_corr_after[i]].peak_str
                  xdisp_rot[i] = corr_db[ss_corr_after[i]].xdisp_rot
                  ydisp_rot[i] = corr_db[ss_corr_after[i]].ydisp_rot
                  xdisp_tot[i] = corr_db[ss_corr_after[i]].xdisp_tot
                  ydisp_tot[i] = corr_db[ss_corr_after[i]].ydisp_tot
                  xdisp[i]     = corr_db[ss_corr_after[i]].ydisp
                  ydisp[i]     = corr_db[ss_corr_after[i]].xdisp
                  file_sot[i]  = corr_db[ss_corr_after[i]].file_sot
                  file_sdo[i]  = corr_db[ss_corr_after[i]].file_sdo
                  t_sot[i]     = corr_db[ss_corr_after[i]].t_sot
                  t_sdo[i]     = corr_db[ss_corr_after[i]].t_sdo
                  dt_sdo[i]    = corr_db[ss_corr_after[i]].dt_sdo
;                 qual_sdo[i]  = corr_db[ss_corr_after[i]].qual_sdo
               endif

            endif

         endelse

      endif

   endfor


endif ; End of initial peak_str and x/ydisp_tot filter


endif

; **********************************************************************
; THIRD (IMPROVED) ESTIMATE of pointing corrections COMPLETED based upon
; the CORR_DB records.
; **********************************************************************

; *********************************************************************
; Now generate derived pointing parameters and update the image headers
; with the best pointing corrections available:
; *********************************************************************

; Correct SOT platescale from fit to measured data:
oindex.cdelt1 = oindex.cdelt1 / 1.015
oindex.cdelt2 = oindex.cdelt1

crval1_sot_cor = $
   comp_fits_crval(xcen, oindex.cdelt1, oindex.naxis1, oindex.crpix1)
crval2_sot_cor = $
   comp_fits_crval(ycen, oindex.cdelt2, oindex.naxis2, oindex.crpix2)

crpix1_sot_cor = $
   comp_fits_crpix(xcen, oindex.cdelt1, oindex.naxis1, crval1_sot_cor)
crpix2_sot_cor = $
   comp_fits_crpix(ycen, oindex.cdelt2, oindex.naxis2, crval2_sot_cor)

; Optional stopping point:
if keyword_set(qstop) then stop

; Update SOT X,YCEN, CRVAL1,2, CRPIX1,2 tags (add X,YCEN tags if they don't exist)
; (N.B. - Here we assumed tags 'XCEN' and 'YCEN' exist for OINDEX) :
oindex.xcen = xcen
oindex.ycen = ycen
oindex.crval1 = crval1_sot_cor
oindex.crval2 = crval2_sot_cor
oindex.crpix1 = crpix1_sot_cor
oindex.crpix2 = crpix2_sot_cor

;*******************************************************************************************
; SECTION 4: ADD VARIOUS TAGS FROM THE CORR DB RECORD TO THE IMAGE HEADER:
;*******************************************************************************************

; Add pointing update-related tags to oindex;
if not tag_exist(oindex, 'corr_db_ver') then oindex = add_tag(oindex, corr_db_ver, 'corr_db_ver') else $
   oindex.corr_db_ver = corr_db_ver
;HELP, corr_db, do_corr_db_update, corr_db_no_overlap, corr_db_not_passed
;STOP, ' Stopping in section 4 - pointing parameter update.'

if not tag_exist(oindex, 'xcenorig') then oindex = add_tag(oindex, xcen_orig,  'xcenorig') else $
   oindex.xcenorig = xcen_orig
if not tag_exist(oindex, 'ycenorig') then oindex = add_tag(oindex, ycen_orig,  'ycenorig') else $
   oindex.ycenorig = ycen_orig
if not tag_exist(oindex, 'xcen_shi') then oindex = add_tag(oindex, xcen_shimizu,  'xcen_shi') else $
   oindex.xcen_shi = xcen_shimizu
if not tag_exist(oindex, 'ycen_shi') then oindex = add_tag(oindex, ycen_shimizu,  'ycen_shi') else $
   oindex.ycen_shi = ycen_shimizu
if not tag_exist(oindex, 'xcen_syn') then oindex = add_tag(oindex, xcen_syn,  'xcen_syn') else $
   oindex.xcen_syn = xcen_syn
if not tag_exist(oindex, 'ycen_syn') then oindex = add_tag(oindex, ycen_syn,  'ycen_syn') else $
   oindex.ycen_syn = ycen_syn
if not tag_exist(oindex, 'xcen_cdb') then oindex = add_tag(oindex, xcen_cdb,  'xcen_cdb') else $
   oindex.xcen_cdb = xcen_cdb
if not tag_exist(oindex, 'ycen_cdb') then oindex = add_tag(oindex, ycen_cdb,  'ycen_cdb') else $
   oindex.ycen_cdb = ycen_cdb

if not tag_exist(oindex, 'dtsecpri') then oindex = add_tag(oindex, dt_sec_reset_prior,  'dtsecpri') else $
   oindex.dtsecpri = dt_sec_reset_prior
if not tag_exist(oindex, 'dtsecaft') then oindex = add_tag(oindex, dt_sec_reset_after,  'dtsecaft') else $
   oindex.dtsecaft = dt_sec_reset_after

if not tag_exist(oindex, 'peak_str') then oindex = add_tag(oindex, peak_str,  'peak_str') else $
   oindex.peak_str = peak_str
if not tag_exist(oindex, 'xdsp_rot') then oindex = add_tag(oindex, xdisp_rot, 'xdsp_rot') else $
   oindex.xdsp_rot = xdisp_rot
if not tag_exist(oindex, 'ydsp_rot') then oindex = add_tag(oindex, ydisp_rot, 'ydsp_rot') else $
   oindex.ydsp_rot = ydisp_rot
if not tag_exist(oindex, 'xdsp_tot') then oindex = add_tag(oindex, xdisp_tot, 'xdsp_tot') else $
   oindex.xdsp_tot = xdisp_tot
if not tag_exist(oindex, 'ydsp_tot') then oindex = add_tag(oindex, ydisp_tot, 'ydsp_tot') else $
   oindex.ydsp_tot = ydisp_tot
if not tag_exist(oindex, 'xdisp')    then oindex = add_tag(oindex, xdisp,     'xdisp')    else $
   oindex.xdisp = xdisp
if not tag_exist(oindex, 'ydisp')    then oindex = add_tag(oindex, ydisp,     'ydisp')    else $
   oindex.ydisp = ydisp
if not tag_exist(oindex, 'file_sot') then oindex = add_tag(oindex, file_sot,  'file_sot') else $
   oindex.file_sot = file_sot
if not tag_exist(oindex, 'file_sdo') then oindex = add_tag(oindex, file_sdo,  'file_sdo') else $
   oindex.file_sdo = file_sdo
if not tag_exist(oindex, 't_sot')    then oindex = add_tag(oindex, t_sot,     't_sot')    else $
   oindex.t_sot = t_sot
if not tag_exist(oindex, 't_sdo')    then oindex = add_tag(oindex, t_sdo,     't_sdo')    else $
   oindex.t_sdo = t_sdo
if not tag_exist(oindex, 'dt_sdo')   then oindex = add_tag(oindex, dt_sdo,    'dt_sdo')   else $
   oindex.dt_sdo = dt_sdo
;if not tag_exist(oindex, 'qual_sdo') then oindex = add_tag(oindex, qual_sdo,  'qual_sdo') else $
;   oindex.qual_sdo = qual_sdo

; Update history tag:
tagval = 'CEN, CRPIX, CRVAL, CROTA, CDELT tags corrected - AGAIN!'
update_history, oindex, tagval, caller='SOT_FIX_POINTING', version=version

if keyword_set(verbose) then begin
   print, 'CRVAL1/2 and X/YCEN tags corrected using SOT-SDO cross correlation.'
   print, 'SOT reference file: ' + ref_file_sot
   print, 'SOT reference time: ' + ref_time_sot
   print, 'Old values: XCEN: ' + string( index.xcen, '$(f8.2)') + ' , ' + $
                      'YCEN: ' + string( index.ycen, '$(f8.2)')
   print, 'New values: XCEN: ' + string(oindex.xcen, '$(f8.2)') + ' , ' + $
                      'YCEN: ' + string(oindex.ycen, '$(f8.2)')
   print, 'PEAK_STR: ' + string(oindex.peak_str, '$(f8.3)')
endif

; Define a correction type array (currently not actually used!, and
; which defaults to '0', meaning, 'use de-rolled synoptic values'):
corr_switch = lonarr(n_img)
ss_prior = where( ((dt_sec_corr_prior lt dt_sec_corr_prior_max) and $
                   (dt_sec_corr_prior lt dt_sec_reset_prior)), n_prior)
if n_prior gt 0 then corr_switch[ss_prior] = 2

ss_after = where( ((dt_sec_corr_after lt dt_sec_corr_after_max) and $
                   (dt_sec_corr_after lt dt_sec_reset_after)), n_after)
if n_after gt 0 then corr_switch[ss_after] = 2

ss_limb = where(sqrt(xcen*xcen + ycen*ycen) ge 800d0, n_limb)
if n_limb gt 0 then corr_switch[ss_limb] = 0

if keyword_set(qstop) then $
   stop, ' Stopping before return from sot_fix_pointing.'

return, oindex

end

