#!/usr/bin/perl
#
# CALIFA automatic reduction pipeline
# Version 1.2 
# March 2011
# S.F.Sanchez
#

#exit;

use Statistics::OLS;
use Math::FFT;
use Math::Stat;
use Math::Spline qw(spline linsearch binsearch);
use Math::Derivative qw(Derivative2);
use Math::Approx;
use Astro::FITS::CFITSIO qw( :longnames :constants );
use PDL;
use PDL::Fit::Polynomial; 
use PDL::Filter::Linear;
use PGPLOT;  # Load PGPLOT module
use PDL::Fit::Gaussian;
use PDL::Slatec;
use PDL::Image2D;

$F3D=$ENV{FIT3D_PATH}; $F3D=$ENV{FIT3D_PATH}; require("$F3D/scripts/my.pl"); #("$F3D/scripts/my.pl");


#
# Configuration variables $F3D=$ENV{FIT3D_PATH}; require("$F3D/scripts/my.pl"); #d for the reduction
#

$PVERSION="1.2";
$convolve=1; # Determine the normalized resolution
$do_ftp=1;
#$convolve=0; # No not determine the normalized resolution
#$do_ftp=0; # Do not copy the results to the FTP


$extinction_global=0.15;

if ($#ARGV<1) {
    print "USE: auto_redu.pl DATE(YYYYMMDD) GLUE[0=NO/1=YES] ARCHIVE_FLUX_CALIB[0=NO/1=YES] [CONVOLVE] [FTP]\n";
    exit;
}


$TODAY=$ARGV[0];
$GLUE=$ARGV[1];
$CALIB=0;
if ($#ARGV==2) {
    $CALIB=$ARGV[2];
}

if ($#ARGV==3) {
    $CALIB=$ARGV[2];
    $convolve=$ARGV[3];
}

if ($#ARGV==4) {
    $CALIB=$ARGV[2];
    $convolve=$ARGV[3];
    $do_ftp=$ARGV[4];
}

$TOMORROW=$TODAY+1;

$DIR_CONF="/disk-b/sanchez/ppak/legacy/"; # Configuration directory where all the relevant configuration files are stored
$DIR_DATA=$DIR_CONF."/DATA/V500/reduced_v".$PVERSION."/"; # Final destination of the reduced data
$DIR_WEB=$DIR_DATA."/web_".$TODAY."/"; # Final destination of the webpage created during the reduction process
 
$DIR_FTP="/reduced/V500/"; # FTP destination
$DIR_FTP_DATA=$DIR_FTP."reduced_v".$PVERSION."/"; # FTP destination of the reduced data
$DIR_FTP_WEB=$DIR_FTP_DATA."/web_".$TODAY."/"; # FTP destination of the webpage
 
open(LOG,">auto_redu.log"); # Log file
open(PROD,">auto_redu.out"); # Products files

$call="mkdir ".$DIR_DATA; # Create the data directory
mycall($call);
$call="mkdir ".$DIR_WEB; # Create the webpage directory
mycall($call);

$call="cp ".$DIR_CONF."/emission_lines_V500.sky ."; # Copy the file with the wavelength of the sky emission lines 
mycall($call);
$call="cp ".$DIR_CONF."/elines_ARC_V500.txt ."; # Copy the file with the wavelength of the ARC emission lines
mycall($call);

$call="cp ".$DIR_CONF."/lat.V500.spec ."; # Look-up table of the wavelength calibration
mycall($call);

#
# Remove the data production of previous reductions.
#

$call="rm -f *cube.fits"; 
mycall($call);
$call="rm -f *.comp_SDSS.ps";
mycall($call);
$call="rm -f *sobj.fits";
mycall($call);
$call="rm -f *rss.fits";
mycall($call);
$call="rm -f *.V.fits";
mycall($call);
$call="rm -f check_w*.ps";
mycall($call);
$call="rm -f SN_*.ps";
mycall($call);
$call="rm -f *_5577*.ps";
mycall($call);
$call="rm -f *_5577*.sky";
mycall($call);
$call="rm -f *.width.ps";
mycall($call);
$call="rm -f *.obj.ps";
mycall($call);
$call="rm -f *.sobj.ps";
mycall($call);
$call="cp ".$DIR_CONF."/CCDFlat.fits .";
mycall($call);
$call="cp ".$DIR_CONF."/telluric.fits .";
mycall($call);
$call="cp ".$DIR_CONF."/ARC_V500.dist.id ARC.dist.id";
mycall($call);
$call="cp ".$DIR_CONF."/ARC_V500.disp.id ARC.disp.id";
mycall($call);
$call="cat /meteo/CAVEX/cavex.dat | grep ".$TODAY." > cavex.dat";
mycall($call);
$call="cat /meteo/CAVEX/cavex.dat | grep ".$TOMORROW." >> cavex.dat";
mycall($call);

#
# We glue all the CCD frames (4 in total) in a single FITs file
#
if ($GLUE==1) {
    print "Glueing the CCD data...\n";
    open(DIR,"ls *a.fits |");
    while($file=<DIR>) {
	chop($file);
	$cut="a.fits";
	$file =~ s/$cut//;
	$call="glue_new_pmas.pl ".$file;
	system($call);
    }
    close(DIR);
    print "DONE\n";
}

$nc=0;
open(FH,"<cavex.dat");
while($line=<FH>) {
    chop($line);
    @data=split(" ",$line);
    $date[$nc]=$data[1].$data[2];
    $av[$nc]=$data[5];
    $nc++;
}
close(FH);



if ($GLUE==1) {
    $call="get_object_V600.pl > object.txt";
    mycall($call);
    


    $call="get_object_ext.pl > object_ext.txt";
    mycall($call);
    

# The Fleaxure Pattern of the different files is determined on the
# basis of the location in the CCD of the spots created by the night-sky lines.
# We measure the spots location
#
    $call="spots_list.pl object.txt ".$DIR_CONF."/spots_V500.short";
    mycall($call);
    $call="plot_spots_all.pl spots_".$TODAY.".ps/CPS 200";
    mycall($call);
}

#
# How many targets are?
#
$i=1;
$n_unc=0;
$n_com=0;
do {
    $OBJ_I="obj_".$i;
    open(FH,"cat object.txt | grep ' $OBJ_I' | wc -l |");
    $nfound=<FH>;
    chop($nfound);
    close(FH);
#    if (($nfound<9)&&($nfound!=0)) {
    if ($nfound>0) {
	if ($nfound<3) {
	    $Jobj[$n_unc]=$i;
	    $n_unc++;
	} else {
	    $n_com++;
	}
    }
#    print "$FFF\n";
    print "# $i $nfound $n_com $n_unc\n";
    $i++;
} while ($nfound!=0);




#
# We perform an statistical analysis of the BIAS level and store the corresponding results
# in the bias.out file, for QC checks.
#
$call="cat object.txt | grep BIAS > bias.txt";
mycall($call);

open(BIAS,"<bias.txt");
open(OUT,">bias.out");
while($line=<BIAS>) {
    chop($line);
    @data=split(" ",$line);
    $file=$data[0];
    open(IMSTAT,"imstats.pl $file 520 1080 50 50 | ");
    while($imstat=<IMSTAT>) {
	chop($imstat);
	@dat_imstat=split(" ",$imstat);
	$mean=$dat_imstat[0];
	$rms=$dat_imstat[1];
	if ((abs($mean-653)<4)&&($rms<3.7)) {
	    print OUT "$file\n";
	}
    }
    close(IMSTAT);
}
close(OUT);
close(BIAS);

$call="wc -l bias.out > nbias.txt";
mycall($call);

open(BIAS,"<nbias.txt");
$line=<BIAS>;
chop($line);
@data=split(" ",$line);
$nbias=$data[0];
close(BIAS);



if ($nbias>3) {
    $call="imcombine.pl bias.out bias.fits";
    mycall($call);
} else {
    if ($nbias>0) {
	$call="cp ".$file." bias.fits";
	mycall($call);
    }
}
if ($nbias>0) {
    $call="med2df.pl bias.fits mbias.fits 5 5";
    mycall($call);
} else {
#
# If there is no bias, we use a master-one
#
    $call="cp ".$DIR_CONF."/mbias_V500.fits .";
    mycall($call);
}



# FIBERFLAT_START
# We combine the SKYFLATS to determine the fiber-to-fiber transmission correction 
# named FIBERFLAT
#
$call="cat object.txt | grep ' sky_1' > sky_1.txt";
mycall($call);
$call="cat object.txt | grep ' Sky_1' >> sky_1.txt";
mycall($call);
$call="cat object.txt | grep ' sky_2' > sky_2.txt";
mycall($call);
$call="cat object.txt | grep ' Sky_2' >> sky_2.txt";
mycall($call);

open(SKY_1,"<sky_1.txt");
open(OUT,">sky_1.out");
while($line=<SKY_1>) {
    chop($line);
    @data=split(" ",$line);
    $file=$data[0];
    open(IMSTAT,"imstats.pl $file 970 1016 50 10 | ");
    while($imstat=<IMSTAT>) {
	chop($imstat);
	@dat_imstat=split(" ",$imstat);
	$mean=$dat_imstat[0];
	$max=$dat_imstat[4];

	if (($mean>5000)&&($max<40000)) { 
	    $call="rm -f b".$file;
	    mycall($call);
	    $call="cp ".$file." b".$file;
	    mycall($call);
	    print OUT "b$file\n";
	}
    }
    close(IMSTAT);
}
close(OUT);
close(SKY_1);

$call="wc -l sky_1.out > nsky_1.txt";
mycall($call);

open(SKY_1,"<nsky_1.txt");
$line=<SKY_1>;
chop($line);
@data=split(" ",$line);
$n_sky_1=$data[0];
close(SKY_1);

print "nsky_1 = $n_sky_1\n";

if ($n_sky_1>2) {
    $call="imcombine.pl sky_1.out sky_1.fits";
    mycall($call);
} else {
    if ($n_sky_1>0) {
	open(SKY,"<sky_1.out");
	$file=<SKY>;
	close(SKY);
	chop($file);
	$call="cp ".$file." sky_1.fits";
	mycall($call);
    }
}




if ($n_sky_1>0) {

#
# Now we reduce the skyflats to produce a fiber-flat
#
    
    $call="cat object.txt | grep cont_sky_1 > cont_sky_1.txt";
    mycall($call);
    open(FH,"<cont_sky_1.txt");
    while($line=<FH>) {
	chop($line);
	@data=split(" ",$line);
	$cont_sky_1=$data[0];
    }
    close(FH);
    
    
    $call="cat object.txt | grep arc_sky_1 > arc_sky_1.txt";
    mycall($call);
    open(FH,"<arc_sky_1.txt");
    while($line=<FH>) {
	chop($line);
	@data=split(" ",$line);
	$arc_sky_1=$data[0];
    }
    close(FH);
    
    #
    # Reduction of the twilight sky-flat frame
    #
    $call="reduce_all.pl sky_1.fits ".$cont_sky_1." ".$arc_sky_1."  1 ".$DIR_CONF."/reduce.noflat.V500.config > reduce_junk.log";
    mycall($call);
    $call="smooth_ff.pl sky_1.disp_cor.fits 7 1 sky_1.poly.fits";
    mycall($call);

    #
    # Determination of the fiberflat and vignetting mask.
    #
    $call="fiber_flat_ppak_new.pl sky_1.poly.fits fiberflat.fits 0.7 mask.fiberflat.fits";
    mycall($call);
    $call="split_ppak.pl mask.fiberflat.fits mask.obj.fits mask.cal.fits mask.sky.fits 0";
    mycall($call);
    $call="Mosaic_rss.pl ".$DIR_CONF."/mos.mask.config mask.rss.fits mask.pt.txt";
    mycall($call);


    #
    # The determine fiber-flat is stored and a basic statistic analysis is performed
    #
    $call="cp fiberflat.fits fiberflat.".$TODAY.".fits";
    mycall($call);
    $call="split_ppak.pl fiberflat.fits fiberflat.obj.fits cal.fits sky.fits 0";
    mycall($call);
    $call="imstats.pl fiberflat.obj.fits 500 165 300 164 > imstats.fiberflat";
    mycall($call);
    dumplog("fiberflat","imstats.fiberflat");
    $call="imstats_hist.pl fiberflat.obj.fits 500 165 300 164 fiberflat.".$TODAY.".ps/CPS 100";
    mycall($call);

    
} else {
#
# If there is no skyflat, we use a master-one
#
    $call="cp ".$DIR_CONF."/fiberflat_V500.fits fiberflat.fits";
    mycall($call);
    $call="cp ".$DIR_CONF."/mask.fiberflat_V500.fits mask.fiberflat.fits";
    mycall($call);
    $call="split_ppak.pl mask.fiberflat.fits mask.obj.fits mask.cal.fits mask.sky.fits 0";
    mycall($call);    
    $call="Mosaic_rss.pl ".$DIR_CONF."/mos.mask.config mask.rss.fits mask.pt.txt";
    mycall($call);

}


#
# FIBERFLAT_END
#


# FLUXCALIB_DETERMINATION_START
# Now we reduce the calibration stars
#


#
# Determines if at least there one calibration star observed.
#
$call="cat object.txt | grep ' std_1' > std_1.txt";
mycall($call);
$nstd_1=0;
open(STD_1,"<std_1.txt");
while($line=<STD_1>) {
    chop($line);
    @data=split(" ",$line);
    $std_1=$data[0];
    $name_std_1=$data[1];
    $cut="std_1_";
    $name_std_1 =~ s/$cut//;
    $nstd_1++;
}
close(STD_1);


#
# If one calibration star is observed we proceed to reduce it.
#

if ($nstd_1>0) {

    $call="cat object.txt | grep ' cont_std_1' > cont_std_1.txt";
    mycall($call);
    open(CONT_STD_1,"<cont_std_1.txt");
    while($line=<CONT_STD_1>) {
	chop($line);
	@data=split(" ",$line);
	$cont_std_1=$data[0];
    }
    close(CONT_STD_1);
    
    $call="cat object.txt | grep ' arc_std_1' > arc_std_1.txt";
    mycall($call);
    open(ARC_STD_1,"<arc_std_1.txt");
    while($line=<ARC_STD_1>) {
	chop($line);
	@data=split(" ",$line);
	$arc_std_1=$data[0];
    }
    close(ARC_STD_1);

#
# Reducing the 1st calibration star
#    
    $call="reduce_all.pl ".$std_1." ".$cont_std_1." ".$arc_std_1."  1 ".$DIR_CONF."/reduce.flat.V500.config > reduce_junk.log";
    mycall($call);

    $pre_std_1=$std_1;
    $pre_std_1 =~ s/.fits//;
    
#
# Extract radial-coadded spectra in consecutive rings of 5" radius (incremental).
#
    if ($TODAY<20110000) {
	$call="radial_sum_rss.pl ".$pre_std_1.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 std_1.rss.fits";
    } else {
	$call="radial_sum_rss.pl ".$pre_std_1.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -3 3 std_1.rss.fits";
    }
    mycall($call);
    $call="img2spec.pl std_1.rss.fits 1 spec_std_1.txt";
    mycall($call);
    

#
# Read the header to extract the information about the Exposure Time, the Airmass and the Observing date.
#
    open(EXPTIME,"read_img_header.pl $std_1 EXPTIME,AIRMASS,DATE-OBS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    close(EXPTIME);
    $factor=1/($exptime); 
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;
    $extinction=$extinction_global;
    $NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
#    while ($date[$NC]<$date_obs) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
    $NC++;
    }
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }

#
# The transmission curve along the wavelength is determined.
#
    $call="calib_det.pl spec_std_1.txt ".$DIR_CONF."/f".$name_std_1.".dat ratio.txt ".$factor." ".$extinction." ".$airmass." 1 11 0 3640 6800";
    mycall($call);

    $call="cp ratio.txt ratio.std1.txt";
    mycall($call);
    


#
# We check if there is a second calibration start, to test the accuracy of the calibration
#

    $n_std2=0;
    $call="cat object.txt | grep ' std_2' > std_2.txt";
    mycall($call);
    open(STD_2,"<std_2.txt");
    while($line=<STD_2>) {
	chop($line);
	@data=split(" ",$line);
	$std_2=$data[0];
	$name_std_2=$data[1];
	$cut="std_2_";
	$name_std_2 =~ s/$cut//;
	$n_std2++;
    }
    close(STD_2);
    
    if ($n_std2>0) {
	$call="cat object.txt | grep ' cont_std_2' > cont_std_2.txt";
	mycall($call);
	open(CONT_STD_2,"<cont_std_2.txt");
	while($line=<CONT_STD_2>) {
	    chop($line);
	    @data=split(" ",$line);
	    $cont_std_2=$data[0];
	}
	close(CONT_STD_2);
	
	$call="cat object.txt | grep ' arc_std_2' > arc_std_2.txt";
	mycall($call);
	open(ARC_STD_2,"<arc_std_2.txt");
	while($line=<ARC_STD_2>) {
	    chop($line);
	    @data=split(" ",$line);
	    $arc_std_2=$data[0];
	}
	close(ARC_STD_2);
	

	open(EXPTIME,"read_img_header.pl $std_2 EXPTIME,AIRMASS,DATE-OBS |");
	$line=<EXPTIME>;
	($file,$exptime,$airmass,$date_obs)=split(" ",$line);
	close(EXPTIME);
	$factor=1/$exptime;
	$date_obs =~ s/T//;
	$date_obs =~ s/\-//g;
	$date_obs =~ s/\://g;
	$extinction=$extinction_global;
	$NC=0;



	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
	    if ($av[$NC]>$extinction) {
		$extinction=$av[$NC];
	    }
	    $NC++;
	}
	if ($extinction>$extinction_global) {
	    $extinction_global=$extinction;
	}



#
# Reducing the 2nd calibration star
#    
    $call="reduce_all.pl ".$std_2." ".$cont_std_2." ".$arc_std_2."  1 ".$DIR_CONF."/reduce.flat.V500.config > reduce_junk.log";
    mycall($call);

    $pre_std_2=$std_2;
    $pre_std_2 =~ s/.fits//;
    
#
# Extract radial-coadded spectra in consecutive rings of 5" radius (incremental).
#
    if ($TODAY<20110000) {
	$call="radial_sum_rss.pl ".$pre_std_2.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 std_2.rss.fits";
    } else {
	$call="radial_sum_rss.pl ".$pre_std_2.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -3 3 std_2.rss.fits";
    }
    mycall($call);
    $call="img2spec.pl std_2.rss.fits 1 spec_std_2.txt";
    mycall($call);
    

#
# Read the header to extract the information about the Exposure Time, the Airmass and the Observing date.
#
    open(EXPTIME,"read_img_header.pl $std_2 EXPTIME,AIRMASS,DATE-OBS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    close(EXPTIME);
    $factor=1/($exptime); 
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;
    $extinction=$extinction_global;
    $NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
#    while ($date[$NC]<$date_obs) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
    $NC++;
    }
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }

#
# The transmission curve along the wavelength is determined.
#
    $call="calib_det.pl spec_std_2.txt ".$DIR_CONF."/f".$name_std_2.".dat ratio.std2.txt ".$factor." ".$extinction." ".$airmass." 1 11 0 3640 6800";
    mycall($call);

	$call="cp ratio.std2.txt ratio.txt";
	system($call);

#	exit;


#
# Full reduction of the second calibration star
#
	
	$call="reduce_all.pl ".$std_2." ".$cont_std_2." ".$arc_std_2."  ".$exptime." ".$DIR_CONF."/reduce.V500.config  ".$airmass." ".$extinction." > reduce_junk.log";
	mycall($call);
    
	$pre_std_2=$std_2;
	$pre_std_2 =~ s/.fits//;
#($pre_std_2,$post)=split(/\./,$std_2);
	

	if ($TODAY<20110000) {
	    $call="radial_sum_rss.pl ".$pre_std_2.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 std_2.rss.fits";
	} else {
	    $call="radial_sum_rss.pl ".$pre_std_2.".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -3 3 std_2.rss.fits";
	}
	mycall($call);
	$call="img2spec.pl std_2.rss.fits 1 spec_std_2.txt";
	mycall($call);
	
	open(CAL,">cal.list");
	$cal_file=$DIR_CONF."/f".$name_std_2.".dat";
	print CAL "$cal_file\n";
	print CAL "$spec_std_2.txt\n";
	close(CAL);
    

#
# We flux-recalibrate the extracted spectrum of the second calibration star.
# calib_test.out contained the MEDIAN and RMS of the flux of the ratio of the
# 10 arcsec/diameter spectrum extracted from the CALIFA data and the flux calibrated
# one obtained from the literature.
# As near is this value as 1, as more stable has been the night.
#
	$call="flux_ratio.pl spec_std_2.txt ".$DIR_CONF."/f".$name_std_2.".dat junk_ratio.txt 1 1 0 1 0 10000";
	mycall($call);
	$call="spec_plot.pl junk_ratio.txt calib_test.ps/CPS 0.4 1.6 3650 6800 > calib_test.out";
	mycall($call);
	
	open(FH,"<calib_test.out");
	$line=<FH>;
	close(FH);
	print LOG "# CALIBRATIION ACCURACY $line";




    }

#
# NORMALIZE_RESOLUTION_START
# We normalize the resolution:
#

    if ($convolve==1) {
	$call="get_resolution_map.pl arc.disp_cor.fits ARC.disp.id get_res_map.out /null";
	mycall($call);
	$call="get_res_plot.pl get_res_map.out 3745 2 'Wavelength' 'Sigma' /null 3700 7800 0 5 1970 7 3.2 get_res_plot.fits";
	mycall($call);
	$call="split_ppak.pl get_res_plot.fits obj.fits cal.fits sky.fits 0";
	mycall($call);
	$call="plot_image_cont.pl obj.fits 0 3 0.51 0.55 '' 1 get_resplot.".$TODAY.".ps/CPS 49 obj.fits 5 0 10 49 rainbow4 0";
	mycall($call);
    } else {
	$call="cp ".$DIR_CONF."/get_res_plot.V500.fits get_res_plot.fits";
	mycall($call);
    }
#
# NORMALIZE_RESOLUTION_END
#
} else {
#
# If there is no calibration star, we use a master flux calibration and the
# master resolution maps.
#
    $call="cp ".$DIR_CONF."/ratio_V500.txt ratio.txt";
    mycall($call);
    $call="cp ".$DIR_CONF."/get_res_plot.V500.fits get_res_plot.fits";
    mycall($call);
}
#exit;

#
# We can override the current night calibration
#

if ($CALIB==1) {
    $call="cp ".$DIR_CONF."/ratio_V500.txt ratio.txt";
    mycall($call);
}


# FLUXCALIB_DETERMINATION_END



#
# Now we reduce the objects
#

#
# We count the number of complete object observations
# If an object is not completely covered during a particular night
# it is possible to reduce partially the objects, pointing to pointing
# and recover them latter (second_glue.pl program).
#
$call="cat object.txt | grep ' obj' | grep 'p3' > complete.txt";
mycall($call);

open(FH,"wc -l complete.txt |");
$line=<FH>;
($nOBJ,$file)=split(" ",$line);
close(FH);
# In the observation of the V500 there are
# single frames per pointing.
#
#$nobj=int($nOBJ/3);
#
$nobj=$nOBJ;
print "$nobj completed\n";

#
# cat object.txt | grep 'obj_' | grep '_p' | grep NGC5947
#

#
# We reduce object by object from the complete.txt list
#


#
# We check that the other two pointings 'p1' and 'p2' 
# were observed during the night.
#
$k=0;
open(FH,"<complete.txt");
while($line=<FH>) {
    chop($line);
    @data=split(" ",$line);
    $name_obj[$k]=$data[1];
    @parts=split(/\_/,$data[1]);
    $cut="obj_".$parts[1]."_p3_";
    $name_obj[$k] =~ s/$cut//;
    $name_obj[$k] =~ s/ //g;
    $J_obj[$k]=$parts[1];
    $NAME_JUST=$name_obj[$k];
    open(P1,"cat object.txt | grep ' obj' | grep '$NAME_JUST' | grep 'p1' | wc -l |");
    $NP1=<P1>;
    chop($NP1);
    close(P1);
    open(P2,"cat object.txt | grep ' obj' | grep '$NAME_JUST' | grep 'p2' | wc -l |");
    $NP2=<P2>;
    chop($NP2);
    close(P2);
    if (($NP1>0)&&($NP2>0)) {
	$k++;
    }
}
close(FH);
#
# We updated the list of objects that are really complete.
#
$nobj=$k;

print "nobj=$nobj, k=$k\n";


#
# REDUCTION_COMPLETE_OBSERVED_TARGETS_START
#
# We reduce the completed objects one by one
#

for ($j=0;$j<$nobj;$j++) {

    #
    # We combine the files if it is $F3D=$ENV{FIT3D_PATH}; require("$F3D/scripts/my.pl"); #d
    # For the V500, with only one frame per pointing, this is not needed.
    #
    $J=$J_obj[$j];
    print "Reducing $name_obj[$j] J='$J' data\n\n";
    $call="cat object.txt | grep ' obj_".$J."_p1' > obj_p1.txt";
    mycall($call);
    $call="cat object.txt | grep ' obj_".$J."_p2' > obj_p2.txt";
    mycall($call);
    $call="cat object.txt | grep ' obj_".$J."_p3' > obj_p3.txt";
    mycall($call);
    
#
# We count the number of frames (for the V500 one).
#
    $call="wc -l obj_p1.txt > n_obj_p1.txt";
    mycall($call);
    open(NC,"<n_obj_p1.txt");
    $ln_obj=<NC>;
    ($n_obj,$junk)=split(" ",$ln_obj);
    chop($n_obj);
    close(NC);

#
# We identify the arc-frame
#
    $call="cat object.txt | grep ' arc_obj_".$J."' > arc_obj.txt";
    mycall($call);
    open(ARC_OBJ,"<arc_obj.txt");
    while($line=<ARC_OBJ>) {
	chop($line);
	@data=split(" ",$line);
	$arc_obj=$data[0];
    }
    close(ARC_OBJ);
#
#
#



#
# READ_HEADER_START 
#
# The header of each particular pointing frame
# and store it in the HEADER.NOW file.
# This is a pipe-separated table used to define the
# final header.
#

    $call="rm -f HEADER.NOW";
    mycall($call);
    for ($i=1;$i<=3;$i++) {
	$file_now="obj_p".$i.".txt";
	open(LH,"<$file_now");
	$ni=0;
	while($lh=<LH>) {
	    chop($lh);
	    @dlh=split(" ",$lh);
	    $head="PPAK_p".$i."_f".$ni;
	    $call="dump_header.pl ".$dlh[0]." ".$head." >> HEADER.NOW";
	    mycall($call);
#
# Velocity Heliocentric determination.
#
	    $call="get_heliocentric_vel_PPAK.pl ".$dlh[0]." > HELIO.NOW";
	    mycall($call);
	    open(HELIO,"<HELIO.NOW");
	    $helio=<HELIO>;
	    chop($helio);
	    close(HELIO);
	    $head_now=$head."_HVEL";
	    open(HELIO,">>HEADER.NOW");
	    print HELIO "$head_now  | $helio\n";
	    close(HELIO);
	    $ni++;
	}
	close(LH);
    }

#
# READ_HEADER_END
#




#
# If more than one frame is observed per pointing, the script combines them
# by a median algorithm.
#
    if ($n_obj>1) {
	$call="imcombine.pl obj_p1.txt obj_p1.fits";
	mycall($call);
	$call="imcombine.pl obj_p2.txt obj_p2.fits";
	mycall($call);
	$call="imcombine.pl obj_p3.txt obj_p3.fits";
	mycall($call);
    } else {
#
# CR_REJECTION_CLEANING_START
#
#
# If only one frame is taken for each pointing, it just proceed to
# clean the CR using the Laplacian technique.
#

	$call="cat obj_p1.txt > obj_all.txt";
	mycall($call);
	$call="cat obj_p2.txt >> obj_all.txt";
	mycall($call);
	$call="cat obj_p3.txt >> obj_all.txt";
	mycall($call);
	$call="rm -rf mean_all.fits";
	mycall($call);
	$call="imcombine.pl obj_all.txt mean_all.fits";
	mycall($call);
	open(NAME,"<obj_p1.txt");
	$lname_now=<NAME>;
	chop($lname_now);
	($name_now,$junk1)=split(" ",$lname_now);
	close(NAME);
	$call="cr_lap_clean.pl ".$name_now." 0.5 10 obj_p1.fits mask_p1.fits";
	mycall($call);
	$spots_now=$name_now;
	$spots_now =~ s/fits/spots/;
	$call="cp ".$spots_now." obj_p1.spots";
	mycall($call);
	open(NAME,"<obj_p2.txt");
	$lname_now=<NAME>;
	chop($lname_now);
	($name_now,$junk2)=split(" ",$lname_now);
	close(NAME);
	$call="cr_lap_clean.pl ".$name_now." 0.5 10 obj_p2.fits mask_p2.fits";
	mycall($call);
	$spots_now=$name_now;
	$spots_now =~ s/fits/spots/;
	$call="cp ".$spots_now." obj_p2.spots";
	mycall($call);
	open(NAME,"<obj_p3.txt");
	$lname_now=<NAME>;
	chop($lname_now);
	($name_now,$junk3)=split(" ",$lname_now);
	close(NAME);
	$call="cr_lap_clean.pl ".$name_now." 0.5 10 obj_p3.fits mask_p3.fits";
	mycall($call);
	$spots_now=$name_now;
	$spots_now =~ s/fits/spots/;
	$call="cp ".$spots_now." obj_p3.spots";
	mycall($call);

#
# CR_REJECTION_CLEANING_END
#


#
# We clean the straigh-light
# So far we have found that the sky-subtraction works well to correct the straigh-light.-
#	$call="straight_light.pl run178_00307.fits 0 tjunk.trc.fits 4 11 staight_light.fits clean.fits 0 10000 0



#
# FLEXURE_DELTA_SHIFT_STARTS
#

	$spots_arc=$arc_obj;
	$spots_arc =~ s/fits/spots/;
	$call="cp ".$spots_arc." arc.spots";
	mycall($call);

# OFFSET 1
	$call="comp_spots.pl obj_p1.spots arc.spots ".$junk1."_spots.ps/CPS 200 > ".$junk1.".offsets";
	mycall($call);
	$spots_file=$junk1.".offsets";
	open(OFF,"<$spots_file");
	$off_line=<OFF>;
	close(OFF);
	chop($off_line);
	($x_med,$y_med,$x_sig,$y_sig)=split(" ",$off_line);
	$dx=0;
	$dy=0;
	if ((abs($x_med)>0.1)&&(abs($x_med)>$x_sig)) {
	    $dx=$x_med;
	}
	if ((abs($y_med)>0.1)&&(abs($y_med)>$y_sig)) {
	    $dy=$y_med;
	}
	if (($dx>0)||($dy>0)) {
	    $call="mv obj_p1.fits tmp.fits";
	    mycall($call);
	    $call="imshift.pl tmp.fits obj_p1.fits ".$dx." ".$dy;
	    mycall($call);
	}

# OFFSET 2
	$call="comp_spots.pl obj_p2.spots arc.spots ".$junk2."_spots.ps/CPS 200 > ".$junk2.".offsets";
	mycall($call);
	$spots_file=$junk2.".offsets";
	open(OFF,"<$spots_file");
	$off_line=<OFF>;
	close(OFF);
	chop($off_line);
	($x_med,$y_med,$x_sig,$y_sig)=split(" ",$off_line);
	$dx=0;
	$dy=0;
	if ((abs($x_med)>0.1)&&(abs($x_med)>$x_sig)) {
	    $dx=$x_med;
	}
	if ((abs($y_med)>0.1)&&(abs($y_med)>$y_sig)) {
	    $dy=$y_med;
	}
	if (($dx>0)||($dy>0)) {
	    $call="mv obj_p2.fits tmp.fits";
	    mycall($call);
	    $call="imshift.pl tmp.fits obj_p2.fits ".$dx." ".$dy;
	    mycall($call);
	}

# OFFSET 3
	$call="comp_spots.pl obj_p3.spots arc.spots ".$junk3."_spots.ps/CPS 200 > ".$junk3.".offsets";
	mycall($call);
	$spots_file=$junk3.".offsets";
	open(OFF,"<$spots_file");
	$off_line=<OFF>;
	close(OFF);
	chop($off_line);
	($x_med,$y_med,$x_sig,$y_sig)=split(" ",$off_line);
	$dx=0;
	$dy=0;
	if ((abs($x_med)>0.1)&&(abs($x_med)>$x_sig)) {
	    $dx=$x_med;
	}
	if ((abs($y_med)>0.1)&&(abs($y_med)>$y_sig)) {
	    $dy=$y_med;
	}
	if (($dx>0)||($dy>0)) {
	    $call="mv obj_p3.fits tmp.fits";
	    mycall($call);
	    $call="imshift.pl tmp.fits obj_p3.fits ".$dx." ".$dy;
	    mycall($call);
	}
#
# FLEXURE_DELTA_SHIFT_END
#


    }

#
# We identify the continuum frame of object $J
#
    $call="cat object.txt | grep ' cont_obj_".$J."' > cont_obj.txt";
    mycall($call);
    open(CONT_OBJ,"<cont_obj.txt");
    while($line=<CONT_OBJ>) {
	chop($line);
	@data=split(" ",$line);
	$cont_obj=$data[0];
    }
    close(CONT_OBJ);

#
#
#


#
# REDUCE_POINTING_1_START
#

#
# We read the header.
#

    open(EXPTIME,"read_img_header.pl obj_p1.fits EXPTIME,AIRMASS,DATE-OBS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;
    $extinction=$extinction_global;
    $NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
	$NC++;
    }

    close(EXPTIME);    

    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }


#
# The exposure time are modified to take into account the aperture correction
# of each fiber. After that the flux is measured in Flux-units/arcsec^2.
#
    $exptime=$exptime*5.64;

    $call="reduce_all.pl obj_p1.fits ".$cont_obj." ".$arc_obj." ".$exptime." ".$DIR_CONF."/reduce.V500.config ".$airmass." ".$extinction." > reduce_junk.log";
    mycall($call);
    

#
# We copy/rename a set of QC files
#

    $call="cp obj_p1.arc.ps ".$name_obj[$j]."_p1.arc.ps";
    mycall($call);

    $call="check_wavelength_cal.pl junk.sky.fits ".$DIR_CONF."/emission_lines_V500.sky 3745 2.0 7 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p1.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p1.ps/CPS 10";
    mycall($call);

    $call="check_wavelength_cal.pl arc.disp_cor.fits ".$DIR_CONF."/emission_lines_V500.arc 3745 2.0 4 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p1.arc.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p1.arc.ps/CPS 10";
    mycall($call);
#
# Accuracy of the wavelength calibration.
#
    $call="table_delta_plot.pl check_wavelength_cal.out 0 1 'V500 Wavelength (\\A) ARC' '\\gD \\gl \\A' check_w_range.".$name_obj[$j]."_p1.arc.ps/CPS 3500 7350 -0.6 0.6";
    mycall($call);

#
# Accuracy of the internal instrumental fitting.
#
    $call="cp obj_p1.width.ps ".$name_obj[$j]."_p1.width.ps";
    mycall($call);
    $call="cp spec_obj_p1.msky.txt spec_".$name_obj[$j]."_p1.msky.txt";
    mycall($call);

    $call="cp obj_p1.mean.width ".$name_obj[$j]."_p1.mean.width ";
    mycall($call);
    $call="rm obj_p1.mean.width";
    mycall($call);
#
# Accuracy of the sky subtraction
#
    $call="get_flux_width.pl junk.sobj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.sobj.flux";
    mycall($call);
    $call="get_flux_width.pl junk.obj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.obj.flux";
    mycall($call);
    $call="table_hist.pl junk.obj.flux 8 ".$name_obj[$j]."_p1_5577.obj.ps/CPS 50 > ".$name_obj[$j]."_p1_5577.obj.sky";
    mycall($call);
    $call="table_hist.pl junk.sobj.flux 8 ".$name_obj[$j]."_p1_5577.sobj.ps/CPS 50 > ".$name_obj[$j]."_p1_5577.sobj.sky";
    mycall($call);


    $call="get_flux_stats.pl obj_p1.sobj.fits 5700 30 3745 2.0 ".$name_obj[$j]."_p1.SN.ps/CPS 1 > ".$name_obj[$j]."_p1.out ";
    mycall($call);

    open(WW,"<table_delta_plot.out");
    $www=<WW>;
    chop($www);
    ($w_offset,$w_rms)=split(" ",$www);
    close(WW);
    $add_line="PIPE_p1_extinction | ".$extinction;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p1_cont | ".$cont_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p1_arc | ".$arc_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p1_w_offset | ".$w_offset;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p1_w_rms | ".$w_rms;
    add_to_file("HEADER.NOW",$add_line);

#
# REDUCE_POINTING_1_END
#



#
# REDUCE_POINTING_2_START
#


    open(EXPTIME,"read_img_header.pl obj_p2.fits EXPTIME,AIRMASS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;
    $extinction=$extinction_global;
    $NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
#    while ($date[$NC]<$date_obs) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
	$NC++;
    }

    close(EXPTIME);   
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }

 
    $exptime=$exptime*5.64;
    $call="reduce_all.pl obj_p2.fits ".$cont_obj." ".$arc_obj." ".$exptime." ".$DIR_CONF."/reduce.V500.config ".$airmass." ".$extinction." > reduce_junk.log";
    mycall($call);

    $call="cp obj_p2.arc.ps ".$name_obj[$j]."_p2.arc.ps";
    mycall($call);

$call="check_wavelength_cal.pl junk.sky.fits ".$DIR_CONF."/emission_lines_V500.sky 3745 2.0 7 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p2.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p2.ps/CPS 10";
    mycall($call);

    $call="check_wavelength_cal.pl arc.disp_cor.fits ".$DIR_CONF."/emission_lines_V500.arc 3745 2.0 4 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p2.arc.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p2.arc.ps/CPS 10";
    mycall($call);
    $call="table_delta_plot.pl check_wavelength_cal.out 0 1 'V500 Wavelength (\A) ARC' '\gD \gl \A' check_w_range.".$name_obj[$j]."_p2.arc.ps/CPS 3500 7350 -0.6 0.6";
    mycall($call);

    open(WW,"<table_delta_plot.out");
    $www=<WW>;
    chop($www);
    ($w_offset,$w_rms)=split(" ",$www);
    close(WW);
    $add_line="PIPE_p2_extinction | ".$extinction;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p2_cont | ".$cont_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p2_arc | ".$arc_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p2_w_offset | ".$w_offset;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p2_w_rms | ".$w_rms;
    add_to_file("HEADER.NOW",$add_line);



    $call="cp obj_p2.width.ps ".$name_obj[$j]."_p2.width.ps";
    mycall($call);
    $call="cp spec_obj_p2.msky.txt spec_".$name_obj[$j]."_p2.msky.txt";
    mycall($call);


    $call="get_flux_width.pl junk.sobj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.sobj.flux";
    mycall($call);
    $call="get_flux_width.pl junk.obj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.obj.flux";
    mycall($call);
    $call="table_hist.pl junk.obj.flux 8 ".$name_obj[$j]."_p2_5577.obj.ps/CPS 50 > ".$name_obj[$j]."_p2_5577.obj.sky";
    mycall($call);
    $call="table_hist.pl junk.sobj.flux 8 ".$name_obj[$j]."_p2_5577.sobj.ps/CPS 50 > ".$name_obj[$j]."_p2_5577.sobj.sky";
    mycall($call);


    $call="cp obj_p2.mean.width ".$name_obj[$j]."_p2.mean.width ";
    mycall($call);
    $call="rm obj_p2.mean.width";
    mycall($call);

#
# REDUCE_POINTING_2_END
#

#
# REDUCE_POINTING_3_START
#
    open(EXPTIME,"read_img_header.pl obj_p3.fits EXPTIME,AIRMASS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;

    $extinction=$extinction_global;
    $NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
#    while ($date[$NC]<$date_obs) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
	$NC++;
    }

    close(EXPTIME);    
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }


#
# We correct for the fibers aperture
#
    $exptime=$exptime*5.64;

    $call="reduce_all.pl obj_p3.fits ".$cont_obj." ".$arc_obj." ".$exptime." ".$DIR_CONF."/reduce.V500.config ".$airmass." ".$extinction." > reduce_junk.log";
    mycall($call);

    $call="cp obj_p3.arc.ps ".$name_obj[$j]."_p3.arc.ps";
    mycall($call);
$call="check_wavelength_cal.pl junk.sky.fits ".$DIR_CONF."/emission_lines_V500.sky 3745 2.0 7 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p3.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p3.ps/CPS 10";
    mycall($call);
    $call="check_wavelength_cal.pl arc.disp_cor.fits ".$DIR_CONF."/emission_lines_V500.arc 3745 2.0 4 1 0";
    mycall($call);
    $call="cp check_wavelength_cal.out check_w.".$name_obj[$j]."_p3.arc.out";
    mycall($call);
    $call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj[$j]."_p3.arc.ps/CPS 10";
    mycall($call);
    $call="table_delta_plot.pl check_wavelength_cal.out 0 1 'V500 Wavelength (\A) ARC' '\gD \gl \A' check_w_range.".$name_obj[$j]."_p3.arc.ps/CPS 3500 7350 -0.6 0.6";
    mycall($call);


    open(WW,"<table_delta_plot.out");
    $www=<WW>;
    chop($www);
    ($w_offset,$w_rms)=split(" ",$www);
    close(WW);
    $add_line="PIPE_p3_extinction | ".$extinction;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p3_cont | ".$cont_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p3_arc | ".$arc_obj;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p3_w_offset | ".$w_offset;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_p3_w_rms | ".$w_rms;
    add_to_file("HEADER.NOW",$add_line);


    $call="cp obj_p3.width.ps ".$name_obj[$j]."_p3.width.ps";
    mycall($call);
    $call="cp spec_obj_p3.msky.txt spec_".$name_obj[$j]."_p3.msky.txt";
    mycall($call);



    $call="get_flux_width.pl junk.sobj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.sobj.flux";
    mycall($call);
    $call="get_flux_width.pl junk.obj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.obj.flux";
    mycall($call);
    $call="table_hist.pl junk.obj.flux 8 ".$name_obj[$j]."_p3_5577.obj.ps/CPS 50 > ".$name_obj[$j]."_p3_5577.obj.sky";
    mycall($call);
    $call="table_hist.pl junk.sobj.flux 8 ".$name_obj[$j]."_p3_5577.sobj.ps/CPS 50 > ".$name_obj[$j]."_p3_5577.sobj.sky";
    mycall($call);

    $call="cp obj_p3.mean.width ".$name_obj[$j]."_p3.mean.width ";
    mycall($call);
    $call="rm obj_p3.mean.width";
    mycall($call);
#
# REDUCE_POINTING_3_END
#


#
# RESCALE_FLUX_BETWEEN_POINTINGS_START
#
# If there is a slight change in the transparence, the pointings need to be rescaled
# 

    if ($TODAY<20110000) {
	$call="radial_sum_rss.pl obj_p1.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -5 3 rad_1.rss.fits";
    } else {
	$call="radial_sum_rss.pl obj_p1.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 rad_1.rss.fits";
    }
    mycall($call);
    $call="img2spec.pl rad_1.rss.fits 3 rad_1.txt";
    mycall($call);
    open(FH,"flux_filter.pl /disk-b/sanchez/ppak/legacy/V_Johnson.txt rad_1.txt 0 |");
    while($L=<FH>) {
	$flux1=$L;
	chop($flux1);
    }
    close(FH);

    if ($TODAY<20110000) {
	$call="radial_sum_rss.pl obj_p2.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 2 9 rad_2.rss.fits";
    } else {
	$call="radial_sum_rss.pl obj_p2.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -5.22 -4.84 rad_2.rss.fits";
    }
    mycall($call);
    $call="img2spec.pl rad_2.rss.fits 3 rad_2.txt";
    mycall($call);
    open(FH,"flux_filter.pl /disk-b/sanchez/ppak/legacy/V_Johnson.txt rad_2.txt 0 |");
    while($L=<FH>) {
	$flux2=$L;
	chop($flux2);
    }
    close(FH);


    if ($TODAY<20110000) {
	$call="radial_sum_rss.pl obj_p3.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 rad_3.rss.fits";
    } else {
	$call="radial_sum_rss.pl obj_p3.sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 -5.22 4.84 rad_3.rss.fits";
    }
    mycall($call);
    $call="img2spec.pl rad_3.rss.fits 3 rad_3.txt";
    mycall($call);
    open(FH,"flux_filter.pl /disk-b/sanchez/ppak/legacy/V_Johnson.txt rad_3.txt 0 |");
    while($L=<FH>) {
	$flux3=$L;
	chop($flux3);
    }
    close(FH);

    print "FLUXES = $flux1 $flux2 $flux3\n";
    print LOG "#FLUXES = $flux1 $flux2 $flux3\n";


    $add_line="PIPE_flux_ratio1 | ".$flux1;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_flux_ratio2 | ".$flux2;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_flux_ratio3 | ".$flux3;
    add_to_file("HEADER.NOW",$add_line);

    @fluxes=($flux1,$flux2,$flux3);
    ($min_flux,$max_flux)=minmax(@fluxes);
    $mean_flux=mean(@fluxes);
    if ($mean_flux!=0) {
	$range_fluxes=($max_flux-$min_flux)/$mean_flux;
    } else {
	$range_fluxes=($max_flux-$min_flux);
    }
    $add_line="PIPE_range_flux | ".$range_fluxes;
    add_to_file("HEADER.NOW",$add_line);

    $F=0.05;
    $call="comp_spec.pl rad_2.txt rad_1.txt rad.txt 5000 5500 101";
    mycall($call);
    open(COMP,"<comp_spec.out");
    $comp=<COMP>;
    chop($comp);
    close(COMP);
    @d_comp=split(" ",$comp);
    $rat12=$d_comp[0];
    if (($flux1>0)&&($flux2>0)) {
	if (($rat12<(1-$F))||($rat12>(1+$F))) {
	    $call="polyfit_spec.pl rad.txt 2 new_rad.txt 20 1900 /null";
	    mycall($call);
	    $call="spec2img.pl new_rad.txt rad.fits 331";
	    mycall($call);
	    $call="imarith.pl obj_p2.sobj.fits '*' rad.fits obj_p2.sobj.fits";
	    mycall($call);
	}
    }

    $call="comp_spec.pl rad_3.txt rad_1.txt rad.txt 5000 5500 101";
    mycall($call);
    open(COMP,"<comp_spec.out");
    $comp=<COMP>;
    chop($comp);
    close(COMP);
    @d_comp=split(" ",$comp);
    $rat13=$d_comp[0];
    if (($flux1>0)&&($flux3>0)) {
	if (($rat13<(1-$F))||($rat13>(1+$F))) {
	    $call="polyfit_spec.pl rad.txt 2 new_rad.txt 20 1900 /null";
	    mycall($call);
	    $call="spec2img.pl new_rad.txt rad.fits 331";
	    mycall($call);
	    $call="imarith.pl obj_p3.sobj.fits '*' rad.fits obj_p3.sobj.fits";
	    mycall($call);
	}
    }


#
# OLD, more simplistic, correction
#
#    if (($flux1>0)&&($flux2>0)) {
#	$rat12=$flux2/$flux1;
#	if (($rat12<0.95)||($rat12>1.05)) {
#	if (($rat12<0.8)||($rat12>1.2)) {
#	    $call="imarith.pl obj_p2.sobj.fits / ".$rat12." obj_p2.sobj.fits";
#	    mycall($call);
#	}
#    }
#    if (($flux1>0)&&($flux3>0)) {
#	$rat13=$flux3/$flux1;
#	if (($rat13<0.95)||($rat13>1.05)) {
#	if (($rat13<0.8)||($rat13>1.2)) {
#	    $call="imarith.pl obj_p3.sobj.fits / ".$rat13." obj_p3.sobj.fits";
#	    mycall($call);
#	}
#    }


#
# RESCALE_FLUX_BETWEEN_POINTINGS_END
#

#
# SPATIAL_REARRANGEMENT_START
#
    
    if ($TODAY<20110000) {
	$call="Mosaic_rss.pl ".$DIR_CONF."/mos_new.config mos_new.rss.fits mos_new.pt.txt";
    } else {
	$call="Mosaic_rss.pl ".$DIR_CONF."/mos_new_2.config mos_new.rss.fits mos_new.pt.txt";
    }
    mycall($call);

#
#    $call="rss2rss_mask_ppak.pl mos_new.rss.fits mos_new.pt.txt mask.rss.fits ".$name_obj[$j].".rss.fits 1";
#    mycall($call);

#
# Filling the spectra affected by vignetting.
#
    $call="rss2rss_mask_ppak.pl mos_new.rss.fits mos_new.pt.txt mask.rss.fits mos_new_masked.rss.fits 1";
    mycall($call);
    
#
# CORRECT_GALACTIC_EXTINCTION_START
#
    $call=$DIR_CONF."/get_par_name.pl ".$DIR_CONF."/CALIFA-parentsample.csv.2mass.galex.IRAS.NAME.chandra.spec.first.NYU ".$name_obj[$j]." 19 > GAL_EXT.txt";
    mycall($call);

    open(EXT,"<GAL_EXT.txt");
    $ext_line=<EXT>;
    chop($ext_line);
    ($pre,$post,$ext_g)=split(/\|/,$ext_line);
    close(EXT);

    if ($ext_g eq "") {
	$add_line="PIPE_gal_ext_cor | 0";
	add_to_file("HEADER.NOW",$add_line);
	$add_line="PIPE_extinction_g | -1";
	add_to_file("HEADER.NOW",$add_line);
	$call="cp mos_new_masked.rss.fits ".$name_obj[$j].".rss.fits";
	mycall($call);
    } else {
	$add_line="PIPE_gal_ext_cor | 1";
	add_to_file("HEADER.NOW",$add_line);
	$add_line="PIPE_extinction_g | ".$ext_g;
	add_to_file("HEADER.NOW",$add_line);
#
# Galactic extinction correction.
#
	$call="correct_galExt_rss.pl mos_new_masked.rss.fits ".$ext_g." 4858 ".$name_obj[$j].".rss.fits";
	mycall($call);
	$call="correct_galExt_rss.pl mos_new.rss.fits ".$ext_g." 4858 mos_new.rss.fits";
	mycall($call);
    }
#
# CORRECT_GALACTIC_EXTINCTION_END
#


#
# Interpolating to create a final regular-grid datacube.
#
    $call="rm -r ".$name_obj[$j].".cube.fits ";
    mycall($call);
    $call="rss2cube_int.pl ".$name_obj[$j].".rss.fits mos_new.pt.txt 1 ".$name_obj[$j].".cube.fits 2 5 1";
    mycall($call);
    $call="cp mos_new.rss.fits mos_".$name_obj[$j].".rss.fits";
    mycall($call);
    $call="cp mos_new.pt.txt mos_".$name_obj[$j].".pt.txt";
    mycall($call);


    print PROD "$name_obj[$j].cube.fits\n";

#
# SPATIAL_REARRANGEMENT_END
#



#
# DIFFERENTIAL_ATMOSPHERIC_REFRACTION_CORRECTION_START
#

#
# We look for the peak intensity!
#
    $call="get_slice.pl ".$name_obj[$j].".cube.fits img /disk-b/sanchez/ppak/legacy/slice_V.conf";
    mycall($call);
    $img=rfits("img_V_4500_5500.fits");
    ($nx,$ny)=$img->dims;
    $val_max=-1e12;
    $XC=37;
    $YC=37;
    for ($ii=30;$ii<45;$ii++) {
	for ($jj=30;$jj<45;$jj++) {
	    $val=$img->at($ii,$jj);
	    if ($val>$val_max) {
		$val_max=$val;
		$XC=$ii;
		$YC=$jj;
	    }
	}
    }


    $Xc=37;
    $Yc=37;
    for ($ii=15;$ii<62;$ii++) {
	for ($jj=15;$jj<62;$jj++) {
	    $val=$img->at($ii,$jj);
	    if ($val>$val_max) {
		$val_max=$val;
		$Xc=$ii;
		$Yc=$jj;
	    }
	}
    }
    
    $call="cp img_V_4500_5500.fits ".$name_obj[$j].".V.fits";
    mycall($call);

    $call="rm -r ".$name_obj[$j].".scube.fits ";
    mycall($call);
    $call="DAR_det_cube.pl ".$name_obj[$j].".cube.fits  ".$Xc." ".$Yc." 3 3 ".$name_obj[$j].".scube.fits 400 1900 3 1 0  0 1";
    mycall($call);


    $add_line="PIPE_DAR_cor_ps | DAR_".$name_obj[$j].".cube.ps";
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_V_4500_5500 | ".$name_obj[$j].".V.fits";
    add_to_file("HEADER.NOW",$add_line);

    $add_line="DATE_OBS | ".$TODAY." ";
    add_to_file("HEADER.NOW",$add_line);

    $call="add_header.pl mos_".$name_obj[$j].".rss.fits HEADER.NOW";
    mycall($call);
    $call="add_header.pl ".$name_obj[$j].".cube.fits HEADER.NOW";
    mycall($call);
    $call="add_header.pl ".$name_obj[$j].".scube.fits HEADER.NOW";
    mycall($call);



    print PROD "$name_obj[$j].scube.fits\n";

#
# DIFFERENTIAL_ATMOSPHERIC_REFRACTION_CORRECTION_END
#




    #
    # FLUX_RECALIBRATION_START
    # 

    #
    # We check the flux recalibration
    #
    
    $call="get_aper_spec_scube.pl ".$name_obj[$j]." V > new_center.txt";
    mycall($call);
    $out_SDSS=$name_obj[$j].".comp_SDSS.out"; 
    $call=$DIR_CONF."/spec_comp_SDSS.pl ".$name_obj[$j].".spec_30.txt none ".$name_obj[$j].".comp_SDSS.ps/CPS 5000 -1 400 3400 8000 > ".$out_SDSS;
    mycall($call);
    open(CSDSS,"<$out_SDSS");
    $csdss=<CSDSS>;
    close(CSDSS);
    chop($csdss);
    ($name_junk,$fact_sdss,$fact_sdss_g,$fact_sdss_r)=split(" ",$csdss);
    if ($fact_sdss>0) {
	$rat=1/$fact_sdss;
	$call="recal_cube_const.pl ".$name_obj[$j].".scube.fits ".$rat." ".$name_obj[$j].".rscube.fits";
	mycall($call);
    }
    



    print PROD "$name_obj[$j].rscube.fits\n";
    $add_line="PIPE_flux_recal | ".$fact_sdss;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_flux_recal_g | ".$fact_sdss_g;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_flux_recal_r | ".$fact_sdss_r;
    add_to_file("HEADER.NOW",$add_line);
    $add_line="PIPE_VERSION | ".$PVERSION;
    add_to_file("HEADER.NOW",$add_line);


    #
    # FLUX_RECALIBRATION_END
    # 


    #
    # We add the header information
    #
    $call="add_header.pl ".$name_obj[$j].".rscube.fits HEADER.NOW";
    mycall($call);    


    #
    # WCS_DETERMINATION_START
    #

    #
    #
    # We get the astrometric solution
    #
    $RA_now=0;
    $DEC_now=0;
    $call=$DIR_CONF."/get_coords.pl ".$DIR_CONF."/CALIFA-parentsample.csv.2mass.galex.IRAS.NAME ".$name_obj[$j]." > coords.txt";
    mycall($call);
    open(TMP,"<coords.txt");
    $tmp=<TMP>; chop($tmp);
    close(TMP);
    @dat_tmp=split(" ",$tmp);
    $RA_now=$dat_tmp[1];
    $DEC_now=$dat_tmp[2];

    if (($RA_now==0)&&($DEC_now==0)) {
	$call="rm -f coords.txt";
	mycall($call);
	$call="wget -nd 'http://nedwww.ipac.caltech.edu/cgi-bin/nph-objsearch?objname=".$name_obj[$j]."&extend=no&hconst=73&omegam=0.27&omegav=0.73&corr_z=1&out_csys=Equatorial&out_equinox=J2000.0&obj_sort=RA+or+Longitude&of=pre_text&zv_breaker=30000.0&list_limit=5&img_stamp=YES&of=ascii_bar' -O coords.txt";
	mycall($call);

	open(TMP,"<coords.txt");
	while($tmp=<TMP>) {
	    chop($tmp);   
	    @dat_tmp=split(/\|/,$tmp);
	    $RA_now=$dat_tmp[2];
	    $DEC_now=$dat_tmp[3];	    
	}	
	close(TMP);

    }
    open(TMP,"<new_center.txt");
    $tmp=<TMP>; chop($tmp);
    close(TMP);
    ($junk,$CX,$CY)=split(" ",$tmp);
    $CX=$CX+0.5;
    $CY=$CY+0.5;

    $call="rm -r HEADER.COORDS";
    mycall($call);
    
    $add_line="WCSAXES |                       2 ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="WCSNAME |    TELESCOPE                                                         ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="RADESYS |    ICRS                                                              ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CTYPE1  |    RA---TAN                                                          ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CUNIT1  |    deg                                                               ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CTYPE2  |    DEC--TAN                                                          ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CUNIT2  |    deg                                                               ";

    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CD1_1   |           -0.0002777777                                              ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CD1_2   |            0.00000                                                   ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CD2_1   |            0.00000                                                   ";
    add_to_file("HEADER.COORDS",$add_line);
    $add_line="CD2_2   |           -0.0002777777     ";
    add_to_file("HEADER.COORDS",$add_line);



    $call="add_header.pl ".$name_obj[$j].".rscube.fits HEADER.COORDS";
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".rscube.fits CRVAL1 ".$RA_now;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".rscube.fits CRVAL2 ".$DEC_now;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".rscube.fits CRPIX1 ".$CX;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".rscube.fits CRPIX2 ".$CY;
    mycall($call);    

    $call="write_img_header.pl ".$name_obj[$j].".V.fits CRVAL1 ".$RA_now;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".V.fits CRVAL2 ".$DEC_now;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".V.fits CRPIX1 ".$CX;
    mycall($call);    
    $call="write_img_header.pl ".$name_obj[$j].".V.fits CRPIX2 ".$CY;
    mycall($call);    

    $call="add_header.pl ".$name_obj[$j].".V.fits HEADER.COORDS";
    mycall($call);    

    #
    # WCS_DETERMINATION_END
    #

    $call="write_img_header.pl ".$name_obj[$j].".rscube.fits FILENAME ".$name_obj[$j].".rscube.fits ";
    mycall($call);    

    $call="get_flux_stats_cube.pl ".$name_obj[$j].".rscube.fits 5800 40 3745 2.0 SN_".$name_obj[$j].".ps/CPS 1 > SN_".$name_obj[$j].".out";
    mycall($call);
    $SNfile="SN_".$name_obj[$j].".out";
    open(SN,"<$SNfile");
    while($SN=<SN>) {
	chop($SN);
	if ($SN !~ "#") {
	    @SN_data=split(" ",$SN);
	    $call="rm -r HEADER.SN";
	    mycall($call);    
	    $add_line="PIPE_VMAG3SIGMA | ".$SN_data[5];
	    add_to_file("HEADER.SN",$add_line);	    
	    $add_line="PIPE_VMAG5SIGMA | ".$SN_data[8];
	    add_to_file("HEADER.SN",$add_line);	    
	    if ($SN_data[1]!=0) {
		$area=$SN_data[6]/$SN_data[1];
	    }
	    $add_line="PIPE_AREA3SIGMA | ".$area;
	    add_to_file("HEADER.SN",$add_line);	    
	    $call="add_header.pl ".$name_obj[$j].".rscube.fits HEADER.SN";
	    mycall($call);    
	}
    }
    close(SN);


#
# Finished the reduction of a complete object.
#

}

#
# REDUCTION_COMPLETE_OBSERVED_TARGETS_END
#




#
# REDUCTION_PARTIAL_OBSERVED_TARGETS_START
#



#
# We check if there are partial observations!
#
$call="cat object.txt | grep ' obj'  > total.txt";
mycall($call);
open(FH,"wc -l total.txt |");
$line=<FH>;
($nTOT,$file)=split(" ",$line);
close(FH);
$ntot=int($nTOT/3);
#$nmore=($nTOT-$ntot*9)/3;


for ($i=0;$i<$n_unc;$i++) {
    
#    $J=$nobj+1;
    $J=$Jobj[$i];

    $N_POINTS=0;
    open(FH,"<total.txt");
    while($line=<FH>) {
	chop($line);
	$OBJ_J="obj_".$J;
	if ($line =~ $OBJ_J) {
	    @data=split(" ",$line);
	    $name_obj_now=$data[1];
	    $cut="obj_".$J."_p1_";
	    $name_obj_now =~ s/$cut//;
	    $cut="obj_".$J."_p2_";
	    $name_obj_now =~ s/$cut//;
	    $cut="obj_".$J."_p3_";
	    $name_obj_now =~ s/$cut//;
	    $name_obj_now =~ s/ //g;
	    $N_POINTS++;
	}
    }
    close(FH);
    $nmore=int($N_POINTS/3);
    if ($N_POINTS != 3*$nmore) {
	$nmore++;
    }

    $call="cat object.txt | grep ' cont_obj_".$J."' > cont_obj.txt";
    mycall($call);
    open(CONT_OBJ,"<cont_obj.txt");
    while($line=<CONT_OBJ>) {
	chop($line);
	@data=split(" ",$line);
	$cont_obj=$data[0];
    }
    close(CONT_OBJ);

    $call="cat object.txt | grep ' arc_obj_".$J."' > arc_obj.txt";
    mycall($call);
    open(ARC_OBJ,"<arc_obj.txt");
    while($line=<ARC_OBJ>) {
	chop($line);
	@data=split(" ",$line);
	$arc_obj=$data[0];
    }
    close(ARC_OBJ);    


    print "Reducing $name_obj_now data $nmore\n\n";
#    exit;
    for ($j=0;$j<$nmore;$j++) {
	$n_p_now=0;
	for ($JJ=1;$JJ<4;$JJ++) {
	    $check="p".$JJ."_".$name_obj_now;
	    open(POINT,"cat total.txt | grep '$check' | wc -l |");
	    $point=<POINT>;
	    chop($point);
	    close(POINT);
	    if ($point>0) {
		$p_now[$n_p_now]=$JJ;
		$n_p_now++;
	    }
	}

#	$K=$j+1;
	$K=$p_now[$j];
	$call="cat object.txt | grep ' obj_".$J."_p".$K."' > obj_p".$K.".txt";
	mycall($call);


    $call="wc -l obj_p".$K.".txt > n_obj_p1.txt";
    mycall($call);
    open(NC,"<n_obj_p1.txt");
    $ln_obj=<NC>;
    ($n_obj,$junk)=split(" ",$ln_obj);
    close(NC);
    if ($n_obj>1) {
	$call="imcombine.pl obj_p".$K.".txt obj_p".$K.".fits";
	mycall($call);
    } else {
	$file_name_now="obj_p".$K.".txt";
	open(NAME,"<$file_name_now");
	$lname_now=<NAME>;
	chop($name_now);
	($name_now,$junk)=split(" ",$lname_now);
	close(NAME);
	$call="cp ".$name_now." obj_p".$K.".fits";
	mycall($call);
    }










	open(EXPTIME,"read_img_header.pl obj_p$K.fits EXPTIME,AIRMASS |");
	$line=<EXPTIME>;
	($file,$exptime,$airmass,$date_obs)=split(" ",$line);
	$date_obs =~ s/T//;
	$date_obs =~ s/\-//g;
	$date_obs =~ s/\://g;

	$extinction=$extinction_global;
	$NC=0;
	while (($date[$NC]<$date_obs)&&($NC<$nc)) {
#	while ($date[$NC]<$date_obs) {
	    if ($av[$NC]>$extinction) {
		$extinction=$av[$NC];
	    }
	    $NC++;
	}

	close(EXPTIME);    
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }

	$call="reduce_all.pl obj_p".$K.".fits ".$cont_obj." ".$arc_obj." ".$exptime." ".$DIR_CONF."/reduce.V500.config ".$airmass." ".$extinction." > reduce_junk.log";
	mycall($call);
	$call="cp obj_p".$K.".sobj.fits ".$name_obj_now."_p".$K.".sobj.fits";
	mycall($call);
	$name_out=$name_obj_now."_p".$K.".sobj.fits";

	print PROD "$name_out\n";


	$call="cp obj_p".$K.".arc.ps ".$name_obj_now."_p".$K.".arc.ps";
	mycall($call);
	$call="check_wavelength_cal.pl junk.sky.fits ".$DIR_CONF."/emission_lines_V500.sky 3745 2.0 7 1 0";
	mycall($call);
	$call="cp check_wavelength_cal.out check_w.".$name_obj_now."_p".$K.".out";
	mycall($call);
	$call="table_hist.pl check_wavelength_cal.all 0 check_w.".$name_obj_now."_p".$K.".ps/CPS 10";
	mycall($call);
	$call="table_delta_plot.pl check_wavelength_cal.out 0 1 'V500 Wavelength (\A) ARC' '\gD \gl \A' check_w_range.".$name_obj_now."_p".$K.".arc.ps/CPS 3500 7350 -0.6 0.6";
	mycall($call);

	$call="cp obj_p".$K.".width.ps ".$name_obj_now."_p".$K.".width.ps";
	mycall($call);
	$call="cp spec_obj_p".$K.".msky.txt spec_".$name_obj_now."_p".$K.".msky.txt";
	mycall($call);



	$call="get_flux_width.pl junk.sobj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.sobj.flux";
	mycall($call);
	$call="get_flux_width.pl junk.obj.fits ".$DIR_CONF."/emission_lines.sky 20 3745 2.0 /null > junk.obj.flux";
	mycall($call);
	$call="table_hist.pl junk.obj.flux 8 ".$name_obj_now."_p".$K."_5577.obj.ps/CPS 50 > ".$name_obj_now."_p".$K."_5577.obj.sky";
	mycall($call);
	$call="table_hist.pl junk.sobj.flux 8 ".$name_obj_now."_p".$K."_5577.sobj.ps/CPS 50 > ".$name_obj_now."_p".$K."_5577.sobj.sky";
	mycall($call);
	
	$call="cp obj_p".$K.".mean.width ".$name_obj_now."_p".$K.".mean.width ";
	mycall($call);







    }

    if ($nmore==1) {
	$call="rm -r ".$name_obj_now.".cube.fits ";
	mycall($call);
     
	$call="rss2cube_int.pl ".$name_obj_now."_p".$p_now[0].".sobj.fits /disk-b/sanchez/ppak/legacy/ppak_pt_arc.txt 1 ".$name_obj_now.".1P.cube.fits 2 5 1";
	mycall($call);

	$call="add_header.pl ".$name_obj_now."_p".$p_now[0].".sobj.fits HEADER.NOW";
	mycall($call);
	$call="add_header.pl ".$name_obj_now.".1P.cube.fits HEADER.NOW";
	mycall($call);
#	$call="add_header.pl ".$name_obj[$j].".scube.fits HEADER.NOW";
#	mycall($call);


	print PROD "$name_obj_now.1P.cube.fits\n";
	$call="get_slice.pl ".$name_obj_now.".1P.cube.fits img /disk-b/sanchez/ppak/legacy/slice_V.conf";
	mycall($call);
	$call="cp img_V_4500_5500.fits ".$name_obj_now.".1P.V.fits";
	mycall($call);

	$call="get_flux_stats_cube.pl ".$name_obj_now.".1P.cube.fits 5800 40 3745 2.0 SN_".$name_obj_now.".1P.ps/CPS 1 > SN_".$name_obj_now.".1P.out";
	mycall($call);

	
    } else {


#	exit;


	$call="cp ".$name_obj_now."_p".$p_now[0].".sobj.fits obj_p".$p_now[0].".sobj.fits";
	mycall($call);
	$call="cp ".$name_obj_now."_p".$p_now[1].".sobj.fits obj_p".$p_now[1].".sobj.fits";
	mycall($call);


	$call="radial_sum_rss.pl obj_p".$p_now[0].".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 rad_1.rss.fits";
	mycall($call);
	$call="img2spec.pl rad_1.rss.fits 4 rad_1.txt";
	mycall($call);
	open(FH,"flux_filter.pl /disk-b/sanchez/ppak/legacy/V_Johnson.txt rad_1.txt 0 |");

    while($L=<FH>) {
	$flux1=$L;
	chop($flux1);
    }
    close(FH);

	
	$call="radial_sum_rss.pl obj_p".$p_now[1].".sobj.fits ".$DIR_CONF."/ppak_pt_arc.txt 5 0 0 rad_2.rss.fits";
	mycall($call);
	$call="img2spec.pl rad_2.rss.fits 4 rad_2.txt";
	mycall($call);
	open(FH,"flux_filter.pl /disk-b/sanchez/ppak/legacy/V_Johnson.txt rad_2.txt 0 |");

    while($L=<FH>) {
	$flux2=$L;
	chop($flux2);
    }
    close(FH);


	print "FLUXES = $flux1 $flux2 \n";
	print LOG "#FLUXES = $flux1 $flux2 \n";    


	$rat12=$flux2/$flux1;
	if (($rat12<0.95)||($rat12>1.05)) {
	    $call="imarith.pl obj_p".$p_now[1].".sobj.fits / ".$rat12." obj_p".$p_now[1].".sobj.fits";
	    mycall($call);
	}

	$PPP=$p_now[0].$p_now[1];
	if ($TODAY<20110000) {
	    $call="Mosaic_rss.pl ".$DIR_CONF."/mos_new_".$PPP."p.config ".$name_obj_now."_2P.rss.fits mos_".$PPP."p.pt.txt";
	} else {
	    $call="Mosaic_rss.pl ".$DIR_CONF."/mos_new_2_".$PPP."p.config ".$name_obj_now."_2P.rss.fits mos_".$PPP."p.pt.txt";
	}
	mycall($call);
	$call=$name_obj_now."_2P.rss.fits";
	print PROD "$call\n";
	$call="cp mos_".$PPP."p.pt.txt ".$DIR_CONF."/";
	mycall($call);
	$call="rm -r ".$name_obj_now.".cube.fits ";
	mycall($call);
#	$call="rss2cube.tcl ".$name_obj_now."_2P.rss.fits mos_".$PPP."p.pt.txt ".$name_obj_now.".2P.cube.fits 3 1e-12 1";
	$call="rss2cube_int.pl ".$name_obj_now."_2P.rss.fits mos_".$PPP."p.pt.txt 1 ".$name_obj_now.".2P.cube.fits 2 5 1";
	mycall($call);
	print PROD "$name_obj_now.2P.cube.fits\n";
	$call="get_slice.pl ".$name_obj_now.".2P.cube.fits img /disk-b/sanchez/ppak/legacy/slice_V.conf";
	mycall($call);
	$call="cp img_V_4500_5500.fits ".$name_obj_now.".2P.V.fits";
	mycall($call);

	$call="get_flux_stats_cube.pl ".$name_obj_now.".2P.cube.fits 5800 40 3745 2.0 SN_".$name_obj_now.".2P.ps/CPS 1 > SN_".$name_obj_now.".2P.out";
	mycall($call);

	$call="add_header.pl ".$name_obj_now."_2P.rss.fits HEADER.NOW";
	mycall($call);
	$call="add_header.pl ".$name_obj_now.".2P.cube.fits HEADER.NOW";
	mycall($call);
#    $call="add_header.pl ".$name_obj[$j].".scube.fits HEADER.NOW";
#    mycall($call);



    }

}


#
# We clean the directory
#
$call="rm -f junk*.fits";
mycall($call);
$call="rm -f arc*.fits";
mycall($call);
#$call="rm -f sky*.fits";
#mycall($call);
$call="rm -f obj_p1.sobj.fits";
mycall($call);
$call="rm -f obj_p2.sobj.fits";
mycall($call);
$call="rm -f obj_p3.sobj.fits";
mycall($call);
$call="rm -f run*b.sobj.fits";
mycall($call);



$nno=0;
open(FH,"<object_ext.txt");
while($line=<FH>) {
    chop($line);
    $a_line[$nno]=$line;
    $nno++;
}
close(FH);

#
# SKYs
#sky
open(SKY,"ls -ltra spec_*msky.txt |");
open(OUTSKY,">auto_redu_V500.sky_list");
open(OUTMAG,">auto_redu_V500.sky_mag");
print OUTMAG "# sky_file V_mag_sky\n";
while($line=<SKY>) {
    chop($line);
    @data=split(" ",$line);
    $file=$data[7];
    $nam=$file;
    $cut="spec_";
    $nam =~ s/$cut//;
    $cut=".msky.txt";
    $nam =~ s/$cut//;
    ($pre,$point)=split(/\_/,$nam);


    $NAME=$point."_".$pre;
    if (($file !~ "run")&&($file !~ "obj")&&($file =~ "_p")&&($pre ne "")) {
	print OUTSKY "$file\n";
	$call="mag_filter.pl ".$DIR_CONF."/filters/V_Johnson.txt 18.89 ".$file." 0 > mag_filter.out";
	mycall($call);
	open(MAG,"<mag_filter.out");
	$a_mag=<MAG>;	
	chop($a_mag);
	$line_now="";
	for ($i=0;$i<$nno;$i++) {
	    @DATA=split(" ",$a_line[$i]);
	    $NAM=$DATA[1];
	    $NAME =~ s/\+//;
	    $NAM =~ s/\+//;
	    if ($NAM =~ $NAME) {
		$line_now=$a_line[$i];
	    }
	}
	
	$point =~ s/p//;
	$call="dump_header.pl ".$pre.".rscube.fits | grep AIRMASS | grep P".$point." > AIRMASS.NOW";
	mycall($call);
	$call="dump_header.pl ".$pre.".rscube.fits | grep JUL_DATE | grep P".$point." > JUL_DATE.NOW";
	mycall($call);

#	exit;

	open(AIRMASS,"<AIRMASS.NOW");
	$AIRMASS=<AIRMASS>;
	@air_dat=split(/\|/,$AIRMASS);
	close(AIRMASS);
	$air_mass_now=$air_dat[1];
	chop($air_mass_now);
	open(AIRMASS,"<JUL_DATE.NOW");
	$AIRMASS=<JUL_DATE>;
	@air_dat=split(/\|/,$AIRMASS);
	close(AIRMASS);
	$jul_date_now=$air_dat[1];
	chop($jul_dat_now);
	print OUTMAG "$a_mag $line_now $jul_date_now $air_mass_now\n";

    }
}
close(OUTMAG);
close(OUTSKY);
close(SKY);

open(SKY_MAG,"<auto_redu_V500.sky_mag");
while($line=<SKY_MAG>) {
    chop($line);
    if ($line !~ "#") {
	@data=split(" ",$line);
	$name=$data[0];
	$cut="spec_";
	$name =~ s/$cut//;
	$cut=".msky.txt";
	$name =~ s/$cut//;
	($namecube,$point)=split(/\_/,$name);
	$mag=$data[2];
	$call="write_img_header.pl ".$namecube.".rscube.fits VMAGSKY".$point." ".$mag;
	mycall($call);    		
    }
}
close(SKY_MAG);


$call="spectra_plot.pl auto_redu_V500.sky_list skys_plot.ps/CPS -1 10";
mycall($call);

$label1="Julian DATE";
$label2="Night-sky V-band (mag/arcsec\u2\d)";
$call="table_plot.pl auto_redu_V500.sky_mag 5 1 '".$label1."' '".$label2."' sky_mag_date.ps/CPS";
mycall($call);

$label1="Airmass";
$label2="Night-sky V-band (mag/arcsec\u2\d)";
$call="table_plot.pl auto_redu_V500.sky_mag 6 1 '".$label1."' '".$label2."' sky_mag_airmass.ps/CPS";
mycall($call);



$call="cat *.mean.width > all.mean.width";
mycall($call);
$call="table_hist.pl all.mean.width 3 all.mean.width.ps/CPS 8";
mycall($call);


open(FH,"<auto_redu_V500.sky_list");
while($file=<FH>) {
    chop($file);
    $psfile=$file;
    $psfile =~ s/txt/ps/;
    $call="spec_plot.pl ".$file." ".$psfile."/CPS -1 10";
    mycall($call);
}
close(FH);

#
# Last check on the wavelength calibration
#
$call=$DIR_CONF."/ana_cal_vel.pl 0";
mycall($call);
$call=$DIR_CONF."/vel_plot_all.pl > vel_plot_all.out";
mycall($call);
$call="grep ABSORP vel_plot_all.out > vel_plot_all.ABS";
mycall($call);

open(ABS,"<vel_plot_all.ABS");
while($line=<ABS>) {
    chop($line);
    @ABS=split(" ",$line);
    $call="write_img_header.pl ".$ABS[1].".rscube.fits PIPE_SYSVEL_MEDIAN ".$ABS[2];
    mycall($call);    
    $call="write_img_header.pl ".$ABS[1].".rscube.fits PIPE_SYSVEL_RMS ".$ABS[3];
    mycall($call);    
}
close(ABS);



#
# We reduce the Velocity stars
#
$i=1;
$n_vstars=0;
do {
    $OBJ_I="vstar_".$i;
    open(FH,"cat object.txt | grep ' $OBJ_I' | wc -l |");
    $nfound=<FH>;
    chop($nfound);
    close(FH);
    if ($nfound>0) {
	$n_vstars++;
    }
    $i++;
} while ($nfound!=0);

print "$nfound V-stars found|n";
print LOG "# $nfound V-stars found|n";
for ($i=0;$i<$n_vstars;$i++) {
    $J=$i+1;
    
    
    $call="cat object.txt | grep ' cont_vstar_".$J."' > cont_vstar.txt";
    mycall($call);
    open(CONT_VSTAR,"<cont_vstar.txt");
    while($line=<CONT_VSTAR>) {
	chop($line);
	@data=split(" ",$line);
	$cont_vstar=$data[0];
    }
    close(CONT_VSTAR);

    $call="cat object.txt | grep ' arc_vstar_".$J."' > arc_vstar.txt";
    mycall($call);
    open(ARC_VSTAR,"<arc_vstar.txt");
    while($line=<ARC_VSTAR>) {
	chop($line);
	@data=split(" ",$line);
	$arc_vstar=$data[0];
    }
    close(ARC_VSTAR);    


    $call="cat object.txt | grep ' vstar_".$J."' > vstar.txt";
    mycall($call);
   open(NAME,"<vstar.txt");
    $line=<NAME>;
    chop($line);
    close(NAME);
    ($junk,$name_vstar)=split(" ",$line);


    $call="imcombine.pl vstar.txt vstar.fits";
    mycall($call);

    open(EXPTIME,"read_img_header.pl vstar.fits EXPTIME,AIRMASS |");
    $line=<EXPTIME>;
    ($file,$exptime,$airmass,$date_obs)=split(" ",$line);
    $date_obs =~ s/T//;
    $date_obs =~ s/\-//g;
    $date_obs =~ s/\://g;
    
    $extinction=$extinction_global;
    $NC=0;
    while (($date[$NC]<$date_obs)&&($NC<$nc)) {
	if ($av[$NC]>$extinction) {
	    $extinction=$av[$NC];
	}
	$NC++;
    }
    
    close(EXPTIME); 
    if ($extinction>$extinction_global) {
	$extinction_global=$extinction;
    }
   
    $call="reduce_all.pl vstar.fits ".$cont_vstar." ".$arc_vstar." ".$exptime." ".$DIR_CONF."/reduce.V500.config ".$airmass." ".$extinction." > reduce_junk.log";
    mycall($call);

    $call="cp vstar.sobj.fits ".$name_vstar."_".$TODAY."_".$J.".V500.sobj.fits";
    mycall($call);
    $name_out=$name_vstar."_".$J.".sobj.fits";
    print PROD "$name_out\n";

}


#
# 
#



#
# We copy all the data to the corresponding final directories
#

$call="get_aper_spec_dir_rscube.pl V";
mycall($call);
$call="cp *V.fits ".$DIR_DATA;
mycall($call);
$call="cp *cube.fits ".$DIR_DATA;
mycall($call);
$call="cp mos_*rss.fits ".$DIR_DATA;
mycall($call);
$call="cp mos_*.pt.txt ".$DIR_DATA;
mycall($call);
$call="cp *.spec_*.txt ".$DIR_DATA;
mycall($call);
$call="cp *_*.sobj.fits ".$DIR_DATA;
mycall($call);

$call="create_web.pl ".$TODAY." 1 2 ".$PVERSION;
mycall($call);

$call="cp web/* ".$DIR_WEB."/";
mycall($call);




if ($do_ftp==1) {
    
    open(ORDERS,">input.ftp");
    print ORDERS "open ftp://mycalifa\@ftp.caha.es\n";
    print ORDERS "mkdir $DIR_FTP_DATA\n";
    print ORDERS "mkdir $DIR_FTP_WEB\n";
    print ORDERS "cd $DIR_FTP_DATA\n";
    print ORDERS "binary\n";
    print ORDERS "mput -f *cube.fits\n";
    print ORDERS "mput -f mos_*rss.fits\n";
    print ORDERS "mput -f mos_*pt.txt\n";
    print ORDERS "mput -f *.spec_*.txt\n";
    print ORDERS "mput -f *_*.sobj.fits\n";
    print ORDERS "cd $DIR_FTP_WEB\n";
    print ORDERS "lcd web\n";
    print ORDERS "mput -f *\n";
    print ORDERS "quit\n";
    close(ORDERS);
    $call="ncftp < input.ftp > output.ftp &";
    mycall($call);
    
}

close(PROD);
close(LOG);


exit;


sub mycall {
    my $call=$_[0];
    print "$call | PROCESSING\n";
    system($call);
    print LOG "$call\n";
    print "DONE\n";
}

sub dumplog {
    my $name=$_[0];
    my $file=$_[1];
    open(DUMP,"<$file");
    my $dd;
    while($dd=<DUMP>) {
	print LOG "# $name | $dd\n";
    }
    close(DUMP);
}

sub add_to_file {
    my $file=$_[0];
    my $line=$_[1];
    open(DUMP,">>$file");
    print DUMP "$line\n";
    close(DUMP);
}

