/******************************************************************************

    put in flag setting; defines for dp mask bits. change
    description.


    PROGRAM:  dbupdate.c
    USAGE:    dbupdate <dbname> <infile>

       This program accesses the CODAS database given by <dbname> for updating.
       The <infile> contains block and profile numbers of profiles for which
       bottom interference has been detected in earlier editing routines
       (newflag and fillgap, or the Matlab interactive
       routines).

       For those profiles with tag other than -1 in the <infile>,

          (1)  the max_amp_bin field in ANCILLARY_2 is set to indicate
               the bin number at which the ocean bottom has been encountered,
               corresponding to the bin at which the amplitude signal reaches
               a maximum (the max_amp_bin field in <infile>);

          (2)  the last_good_bin field in ANCILLARY_2 is reset to its
               default, conf1.num_bins, for further updating by set_lgb.

          (3)  the last_good_bin field in ACCESS_VARIABLES is set to the
               same value as the last_good_bin field in ANCILLARY_2 if
               the latter has a smaller value.

       For those profiles tagged as -1 in the <infile>,
       all the bins are considered bad so last_good_bin is set to
       -1 for both ANCILLARY_2 and ACCESS_VARIABLES.


       J. Ranada - 03/08/88 - University of Hawaii JIMAR

       Modified 10/17/89 to perform two passes:  Pass 1 checks the
       max_amp_bin field for the <infile> whenever the tag is not equal to -1
       to see if it has been properly set (not a MAXSHORT) and aborts
       the program if there are errors in the <infile>;  otherwise,
       Pass 2 continues with the actual updating of the database as
       described above. - JR
                                                                              *
******************************************************************************/

#include "geninc.h"
#include "data_id.h"            /* CODAS variable names and IDs   */
#include "adcp.h"               /* ADCP data structure typedefs   */
#include "ioserv.h"             /* non_blank(), check_fopen()     */
#include "use_db.h"             /* db*_cnf(), write_ymdhms_time() */
#include "dbedit.h"             /* comment(), update_acc_var()    */
#include "dpmask.h"


static char dbname[256], infile[256];

#if PROTOTYPE_ALLOWED
int set_block_dpmask(int bit_num)
#else
int set_block_dpmask(bit_num)
int bit_num;
#endif
{
   ULONG dpmask;
   unsigned int nmask = sizeof(ULONG);

   if (dbget_cnf(DATA_PROC_MASK, (char *) &dpmask, &nmask, "getting data processing mask"))
      return(1);
/*   printf("\nbit: %d, before slb: %ld", bit_num, dpmask); */
   set_long_bit((FILE *) NULL, (char *) &dpmask, bit_num);
/*   printf("  after slb: %ld ", dpmask); */
   if (dbput_cnf(DATA_PROC_MASK, (char *) &dpmask, &nmask, "storing data processing mask"))
      return(1);
   return(0);
}


#if PROTOTYPE_ALLOWED
int main(int argc, char *argv[])
#else
int main(argc, argv)
int argc;
char *argv[];
#endif
{
   char             buff[255];
   int              tag, max_amp_bin, file_OK = 1;
   int              undo = 0, iarg, print_usage = 0;
   YMDHMS_TIME_TYPE time;
   ANCILLARY_2_TYPE anc;
   CONFIGURATION_1_TYPE conf1;

   FILE             *fpin;
   unsigned int     n;

   iarg = 1;
   if (argc == 4)
   {
      if (strcmp(argv[iarg], "-u") == 0)
      {
         undo = 1;
         iarg++;
         argc--;
      }
      else
      {
         print_usage = 1;
      }
   }
   if (argc != 3)
   {
      print_usage = 1;
   }
   else
   {
      strncpy(dbname, argv[iarg++], 255);
      strncpy(infile, argv[iarg], 255);
   }



   if (print_usage)
   {
      printf("\n ERROR: Invalid arguments on command line.");
      printf("\n USAGE: dbupdate [-u] <dbname> <infile>\n\n");
      printf("\n        -u option means undo\n\n");
      exit(-1);
   }

   fpin = check_fopen(infile, "r");
   printf("\n\n PASS 1: Checking input file %s\n\n", infile);
   while (fgets(buff, 255, fpin))
   {
      if (!comment(non_blank(buff)))
      {
         if (sscanf(buff,"%d", &tag) != 1)
         {
            printf("\n ERROR: Scanning <infile> line:\n %s\n", buff);
            exit(-1);
         }
         if (tag != -1)
         {
            if (sscanf(buff, "%*d %*d %*d %*d/%*d/%*d %*d:%*d:%*d %*c%*c%*c%*c %*d %d",
                       &max_amp_bin) != 1)
            {
               printf("\n ERROR: Scanning <infile> line:\n %s\n", buff);
               exit(-1);
            }
            if (max_amp_bin == MAXSHORT)
            {
               file_OK = 0;
               buff[79] = '\0';
               printf("%s\n", buff);
            }
         }
      }
   }

   if (!file_OK)
   {
      printf("\n ERROR: max_amp_bin not properly set for above line(s)");
      printf("\n dbupdate aborted\n\n");
      exit(-1);
   }

   printf("\n\n PASS 2: Updating database %s\n\n", dbname);
   if (dbopen_cnf(1, dbname, READ_WRITE, DIR_IN_MEMORY)) exit(-1);
   rewind(fpin);
   while (fgets(buff, 255, fpin))
   {
      if (!comment(non_blank(buff)))
      {
         if (sscanf(buff,"%d %*d %*d %hd/%hd/%hd %hd:%hd:%hd",
            &tag, &(time.year), &(time.month), &(time.day),
            &(time.hour), &(time.minute), &(time.second)) != 7)
         {
            printf("\n ERROR: Scanning <infile> line:\n  %s", buff);
            goto close_db;
         }
         time.year = yr4digit(time.year);
         printf("\n...Processing ");
         write_ymdhms_time(stdout, &time);

         if (dbsrch_cnf(TIME_SEARCH, (char *) &time)) goto close_db;

         n = sizeof(CONFIGURATION_1_TYPE);
         if (dbget_cnf(CONFIGURATION_1, (char *) &conf1, &n, "getting configuration data"))
            goto close_db;

         n = sizeof(ANCILLARY_2_TYPE);
         if (dbget_cnf(ANCILLARY_2, (char *) &anc, &n, "getting ancillary data"))
            goto close_db;

         if (tag == -1)
         {
            anc.last_good_bin = -1;                         /* all bins are bad */
            if (undo)
            {
               anc.last_good_bin = conf1.num_bins;
            }
            if (update_acc_var(anc.last_good_bin)) goto close_db;
         }
         else
         {
            sscanf(buff,"%*d %*d %*d %*d/%*d/%*d %*d:%*d:%*d %*c%*c%*c%*c %*d %hd",
                   &(anc.max_amp_bin));
            anc.last_good_bin = conf1.num_bins;      /* reset to default;
                                                      alter later */
            if (undo)
            {
               anc.max_amp_bin = MAXSHORT;
            }
            if (error_found(set_block_dpmask(BOTTOM_SOUGHT),
               "setting data processing mask")) return(1);
            if (error_found(set_block_dpmask(100 + BOTTOM_MGB),
               "clearing data processing mask")) return(1);
         }

         if (dbput_cnf(ANCILLARY_2, (char *) &anc, &n, "storing ancillary data"))
            goto close_db;
      }
   }

   close_db:
      fclose(fpin);
      dbclose_cnf();
      return(0);
}
