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

SIMSERCH:   This program facilitates searching through the SIMIBM.IDX file
            available from the SIMTEL archives.  It supports keyword searches
            within selectable fields, starting and ending date boundaries,
            and user specified index files.  It can also create (or append to)
            a SIMTEL request file which is suitable for e-mailing to the
            SIMTEL list servers.

            This program will compile and run under Turbo-C 2.0 and
            VAX/VMS C.

            This program is FREEWARE, and comes with NO WARRANTEES,
            expressed or implied.

   Author:  Richard W. Hull <hull@skvax1.csc.ti.com>

   Acknowledgements:
            Ed. Mueller and Larry Johnson for providing valuable inputs and
            for insisting that I submit the results to SIMTEL.
 
   Usage:   simserch [?]
                     [-s[fdnx] search-string]
                     [-d[se] start/end date]
                     [-i index-file]
                     [-r[a] simtel-request-file]
 
******************************************************************************/
 
#include <stdio.h>
#include <string.h>
 
#ifdef VAX11C
char *strlwr( char *arg )
{
   char *arg_save = arg;
 
   while( *arg )
   {
      *arg = tolower( *arg );
      arg++;
   }
   return( arg_save );
}
#endif
 
int main( int argc, char *argv[] )
 
{
FILE  *index_file, *simreq_file;         /* input file */
char  fs[10],dir[60],name[15],descr[60]; /* input variables */
char  inputline[257];                    /* for initial read */
int   rev,bits;                          /* input variables */
long  length,date,sdate,edate;           /* input variables */
char  lfs[10],ldir[60];                  /* stores last filesystem/directory */
char  type;                              /* output variable for 'A' or 'B' */
char  searchstr[40];                     /* string to qualify entries */
int   search_fs, search_dir,
      search_name, search_desc;          /* indicates which fields to search */
char  teststr[257];                      /* combo of fs,dir,name,descr */
char  ndxfilnam[100];                    /* name of input index file */
char  reqfilnam[100];                    /* SIMTEL request file */
int   append_to_req;                     /* Flag for opening SIMTEL req file */
long  tot_files, sel_files;              /* total, selected files */
long  tot_ldate, sel_ldate;              /* total, selected last date */
char  c;                                 /* picks off EOF,",linefeed */
int   i,j;

sdate = 0;
edate = 999999;
searchstr[0] = '\0';
#ifdef VAX11C
strcpy( ndxfilnam, "USER2:[HULL]SIMIBM.IDX" );
#else
strcpy( ndxfilnam, "simibm.idx" );
#endif
reqfilnam[0] = '\0';
tot_files = sel_files = tot_ldate = sel_ldate = 0;
 
if (argc > 1 && strstr( argv[1], "?" ))
{
   printf( "Usage:  simserch [?]\n" );
   printf( "                 [-s[fdnx] search-string]\n" );
   printf( "                 [-i index-file-name]\n" );
   printf( "                 [-d[se] start/end date]\n" );
   printf( "                 [-r[a] simtel-request-file]\n" );
   printf( "\n" );
   printf( "  -s [f search FILE-SYSTEM\n" );
   printf( "      d        DIRECTORY\n" );
   printf( "      n        NAME\n" );
   printf( "      x        DESCRIPTION]\n" );
   printf( "     Default is to search ALL fields.\n" );
   printf( "\n" );
   printf( "  -d [s starting date\n" );
   printf( "      e ending date]\n" );
   printf( "     Default is Starting-Date\n" );
   printf( "     Date format is YYMMDD.\n" );
   printf( "\n" );
   printf( "  -r [a append to Request File]\n" );
   printf( "     Default is to Overwrite Request File.\n" );
 
   exit(0);
}
 
if (!(argc % 2))
{
   printf( "Invalid number of parameters\n\n" );
   exit(0);
}
 
printf("Simtel.Net Public Domain, Freeware and Shareware listing\n\n");
 
for (i=1; i<argc; i+=2)
{
   if (strstr( argv[i], "-s" ))
   {
      search_fs = search_dir = search_name = search_desc = 0;
      strcpy( searchstr, argv[i+1] );
      strlwr( searchstr );
 
      /* Look for mention of specific fields to search */
 
      if (strstr( argv[i], "f" )) search_fs   = 1;
      if (strstr( argv[i], "d" )) search_dir  = 1;
      if (strstr( argv[i], "n" )) search_name = 1;
      if (strstr( argv[i], "x" )) search_desc = 1;
 
      /* If no specific fields were mentioned, search everything */
 
      if (!(search_fs || search_dir || search_name || search_desc))
         search_fs = search_dir = search_name = search_desc = 1;
   }
 
   if (strstr( argv[i], "-d" ))
   {
      if (strstr( argv[i], "e" ))
         sscanf( argv[i+1], "%ld", &edate );
      else
         sscanf( argv[i+1], "%ld", &sdate );

      if (strstr( argv[i], "s" ))
         sscanf( argv[i+1], "%ld", &sdate );
   }

   if (!strcmp( "-i", argv[i] ))
   {
      strcpy( ndxfilnam, argv[i+1] );
      strlwr( ndxfilnam );
   }

   if (strstr( argv[i], "-r" ))
   {
      strcpy( reqfilnam, argv[i+1] );
      strlwr( reqfilnam );
      append_to_req = (argv[i][2] == 'a');
   }
}

if (searchstr[0])
{
   printf( "Will search " );
   if (search_fs)   printf( "FILE-SYSTEM " );
   if (search_dir)  printf( "DIRECTORY " );
   if (search_name) printf( "NAME " );
   if (search_desc) printf( "DESCRIPTION " );
   printf( "for: %s\n", searchstr );
}

if (sdate > 0)
   printf( "Starting Date: %ld\n", sdate );

if (edate < 999999)
   printf( "Ending Date:   %ld\n", edate );

printf( "Index File to be searched is: %s\n", ndxfilnam );
 
if (!(index_file = fopen( ndxfilnam, "r" )))
{
   printf( "\nCould not open Index File: %s\n", ndxfilnam );
   exit(0);
}
 
if (reqfilnam[0])
{
   char open_mode[4];
 
   if (append_to_req)
   {
      strcpy( open_mode, "a" );
      printf( "Selected Files will be appended to: %s\n", reqfilnam );
   }
   else
   {
      strcpy( open_mode, "w" );
      printf( "Selected Files will be written to: %s\n", reqfilnam );
   }
 
   if (!(simreq_file = fopen( reqfilnam, open_mode )))
   {
      printf( "\nCould not open Request File: %s\n", reqfilnam );
      exit(0);
   }
}
 
printf("\nNOTE: Type B is Binary; Type A is ASCII\n");
 
inputline[256] = 0;
 
while (fgets(inputline, 256, index_file) != NULL)  {
 
   sscanf(inputline,
            "\"%[^\"]\",\"%[^\"]\",\"%[^\"]\",%d,%ld,%d,%ld,\"%[^\"]\"",
            fs, dir, name, &rev, &length, &bits, &date, descr);
 
   tot_files++;
   if (date > tot_ldate) tot_ldate = date;
 
   if (date < sdate) continue;
   if (date > edate) continue;
 
   teststr[0] = '\0';
   if (search_fs)
   {
      strcat( teststr, fs );
      strcat( teststr, " " );
   }
   if (search_dir)
   {
      strcat( teststr, dir );
      strcat( teststr, " " );
   }
   if (search_name)
   {
      strcat( teststr, name );
      strcat( teststr, " " );
   }
   if (search_desc)
   {
      strcat( teststr, descr );
      strcat( teststr, " " );
   }
/*
   sprintf( teststr, "%s %s %s %s", fs, dir, name, descr );
*/
   strlwr( teststr );
 
   if (  (searchstr[0]) && !( strstr( teststr, searchstr ) ) )
      continue;
 
   sel_files++;
   if (date > sel_ldate) sel_ldate = date;
 
   type = 'B';                           /* Binary 8-bit */
   if (bits == 7) type = 'A';            /* ASCII  7-bit */
 
   if (strcmp(ldir,dir) || strcmp(lfs,fs)) {  /* New Directory */
      printf("\nDirectory %s%s\n",fs,dir);
      printf(" Filename   Type Length   Date    Description\n");
      printf("==============================================\n");
      strcpy(ldir, dir);          /* Remember last directory with ldir  */
      strcpy(lfs,fs);             /* Remember last file system with lfs */
   }                              /* End of the New Directory routine   */
 
 
   printf("%-12.12s  %c %7ld  %6ld  %s\n",name,type,length,date,descr);
 
   if (reqfilnam[0]) fprintf( simreq_file, "/PDGET %s%s%s UUENCODE\n",
                                             fs, dir, name );
   }
 
if (reqfilnam[0]) fclose( simreq_file );
 
printf( "\n\nNumber of Files (Total/Processed): %ld / %ld\n",
        tot_files, sel_files );
printf( "Last Date for Files (Total/Processed): %ld / %ld\n",
        tot_ldate, sel_ldate );
 
return (1) ;
 
} /* end of main() */

