169495Sbostic // -*- C++ -*-
269495Sbostic /* Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
369495Sbostic      Written by James Clark (jjc@jclark.com)
469495Sbostic 
569495Sbostic This file is part of groff.
669495Sbostic 
769495Sbostic groff is free software; you can redistribute it and/or modify it under
869495Sbostic the terms of the GNU General Public License as published by the Free
969495Sbostic Software Foundation; either version 2, or (at your option) any later
1069495Sbostic version.
1169495Sbostic 
1269495Sbostic groff is distributed in the hope that it will be useful, but WITHOUT ANY
1369495Sbostic WARRANTY; without even the implied warranty of MERCHANTABILITY or
1469495Sbostic FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
1569495Sbostic for more details.
1669495Sbostic 
1769495Sbostic You should have received a copy of the GNU General Public License along
1869495Sbostic with groff; see the file COPYING.  If not, write to the Free Software
1969495Sbostic Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
2069495Sbostic 
2169495Sbostic #include <stdlib.h>
22*69502Sbostic #include <unistd.h>
2369495Sbostic #include <stdio.h>
2469495Sbostic #include <errno.h>
2569495Sbostic #include <string.h>
2669495Sbostic #include <assert.h>
2769495Sbostic 
2869495Sbostic #include "lib.h"
2969495Sbostic #include "errarg.h"
3069495Sbostic #include "error.h"
3169495Sbostic 
3269495Sbostic #include "defs.h"
3369495Sbostic #include "refid.h"
3469495Sbostic #include "search.h"
3569495Sbostic 
usage()3669495Sbostic static void usage()
3769495Sbostic {
3869495Sbostic   fprintf(stderr, "usage: %s [-nv] [-p database] [-i XYZ] [-t N] keys ...\n",
3969495Sbostic 	  program_name);
4069495Sbostic   exit(1);
4169495Sbostic }
4269495Sbostic 
main(int argc,char ** argv)4369495Sbostic main(int argc, char **argv)
4469495Sbostic {
4569495Sbostic   program_name = argv[0];
4669495Sbostic   static char stderr_buf[BUFSIZ];
4769495Sbostic   setbuf(stderr, stderr_buf);
4869495Sbostic   int search_default = 1;
4969495Sbostic   search_list list;
5069495Sbostic   int opt;
5169495Sbostic   while ((opt = getopt(argc, argv, "nvVi:t:p:")) != EOF)
5269495Sbostic     switch (opt) {
5369495Sbostic     case 'V':
5469495Sbostic       verify_flag = 1;
5569495Sbostic       break;
5669495Sbostic     case 'n':
5769495Sbostic       search_default = 0;
5869495Sbostic       break;
5969495Sbostic     case 'i':
6069495Sbostic       linear_ignore_fields = optarg;
6169495Sbostic       break;
6269495Sbostic     case 't':
6369495Sbostic       {
6469495Sbostic 	char *ptr;
6569495Sbostic 	long n = strtol(optarg, &ptr, 10);
6669495Sbostic 	if (n == 0 && ptr == optarg) {
6769495Sbostic 	  error("bad integer `%1' in `t' option", optarg);
6869495Sbostic 	  break;
6969495Sbostic 	}
7069495Sbostic 	if (n < 1)
7169495Sbostic 	  n = 1;
7269495Sbostic 	linear_truncate_len = int(n);
7369495Sbostic 	break;
7469495Sbostic       }
7569495Sbostic     case 'v':
7669495Sbostic       {
7769495Sbostic 	extern const char *version_string;
7869495Sbostic 	fprintf(stderr, "GNU lkbib version %s\n", version_string);
7969495Sbostic 	fflush(stderr);
8069495Sbostic 	break;
8169495Sbostic       }
8269495Sbostic     case 'p':
8369495Sbostic       list.add_file(optarg);
8469495Sbostic       break;
8569495Sbostic     case '?':
8669495Sbostic       usage();
8769495Sbostic     default:
8869495Sbostic       assert(0);
8969495Sbostic     }
9069495Sbostic   if (optind >= argc)
9169495Sbostic     usage();
9269495Sbostic   char *filename = getenv("REFER");
9369495Sbostic   if (filename)
9469495Sbostic     list.add_file(filename);
9569495Sbostic   else if (search_default)
9669495Sbostic     list.add_file(DEFAULT_INDEX, 1);
9769495Sbostic   if (list.nfiles() == 0)
9869495Sbostic     fatal("no databases");
9969495Sbostic   int total_len = 0;
10069495Sbostic   for (int i = optind; i < argc; i++)
10169495Sbostic     total_len += strlen(argv[i]);
10269495Sbostic   total_len += argc - optind - 1 + 1; // for spaces and '\0'
10369495Sbostic   char *buffer = new char[total_len];
10469495Sbostic   char *ptr = buffer;
10569495Sbostic   for (i = optind; i < argc; i++) {
10669495Sbostic     if (i > optind)
10769495Sbostic       *ptr++ = ' ';
10869495Sbostic     strcpy(ptr, argv[i]);
10969495Sbostic     ptr = strchr(ptr, '\0');
11069495Sbostic   }
11169495Sbostic   search_list_iterator iter(&list, buffer);
11269495Sbostic   const char *start;
11369495Sbostic   int len;
11469495Sbostic   for (int count = 0; iter.next(&start, &len); count++) {
11569495Sbostic     if (fwrite(start, 1, len, stdout) != len)
11669495Sbostic       fatal("write error on stdout: %1", strerror(errno));
11769495Sbostic     // Can happen for last reference in file.
11869495Sbostic     if (start[len - 1] != '\n')
11969495Sbostic       putchar('\n');
12069495Sbostic     putchar('\n');
12169495Sbostic   }
12269495Sbostic   exit(!count);
12369495Sbostic }
124