home *** CD-ROM | disk | FTP | other *** search
- /* $Id: artsrch.c,v 4.4.3.1 1992/02/01 03:09:32 sob PATCH_3 sob $
- *
- * $Log: artsrch.c,v $
- * Revision 4.4.3.1 1992/02/01 03:09:32 sob
- * Release 4.4 Patchlevel 3
- *
- * Revision 4.4.2.1 1991/12/01 18:05:42 sob
- * Patchlevel 2 changes
- *
- * Revision 4.4 1991/09/09 20:18:23 sob
- * release 4.4
- *
- *
- *
- */
- /* This software is Copyright 1991 by Stan Barber.
- *
- * Permission is hereby granted to copy, reproduce, redistribute or otherwise
- * use this software as long as: there is no monetary profit gained
- * specifically from the use or reproduction of this software, it is not
- * sold, rented, traded or otherwise marketed, and this copyright notice is
- * included prominently in any copy made.
- *
- * The author make no claims as to the fitness or correctness of this software
- * for any use whatsoever, and it is provided as is. Any use of this software
- * is at the user's own risk.
- */
-
- #include "EXTERN.h"
- #include "common.h"
- #include "search.h"
- #include "term.h"
- #include "util.h"
- #include "intrp.h"
- #include "bits.h"
- #include "kfile.h"
- #include "head.h"
- #include "final.h"
- #include "cheat.h"
- #ifdef SERVER
- #include "server.h"
- #endif
- #include "ng.h"
- #include "artio.h"
- #ifdef USETHREADS
- #include "threads.h"
- #include "rthreads.h"
- #include "ngdata.h"
- #endif
- #include "INTERN.h"
- #include "artsrch.h"
-
- void
- artsrch_init()
- {
- #ifdef ARTSEARCH
- #ifdef ZEROGLOB
- init_compex(&sub_compex);
- init_compex(&art_compex);
- #endif
- #endif
- }
-
- /* search for an article containing some pattern */
-
- #ifdef ARTSEARCH
- int
- art_search(patbuf,patbufsiz,get_cmd)
- char *patbuf; /* if patbuf != buf, get_cmd must */
- int patbufsiz;
- int get_cmd; /* be set to FALSE!!! */
- {
- char *pattern; /* unparsed pattern */
- register char cmdchr = *patbuf; /* what kind of search? */
- register char *s;
- bool backward = cmdchr == '?' || cmdchr == Ctl('p');
- /* direction of search */
- COMPEX *compex; /* which compiled expression */
- char *cmdlst = Nullch; /* list of commands to do */
- int normal_return = SRCH_NOTFOUND; /* assume no commands */
- bool saltaway = FALSE; /* store in KILL file? */
- char howmuch; /* search just the subjects */
- bool doread; /* search read articles? */
- bool foldcase = TRUE; /* fold upper and lower case? */
-
- int_count = 0;
- if (cmdchr == '/' || cmdchr == '?') { /* normal search? */
- if (get_cmd && buf == patbuf)
- if (!finish_command(FALSE)) /* get rest of command */
- return SRCH_ABORT;
- compex = &art_compex;
- if (patbuf[1]) {
- howmuch = 0;
- doread = FALSE;
- }
- else {
- howmuch = art_howmuch;
- doread = art_doread;
- }
- s = cpytill(buf,patbuf+1,cmdchr);/* ok to cpy buf+1 to buf */
- pattern = buf;
- if (*pattern) {
- if (*lastpat)
- free(lastpat);
- lastpat = savestr(pattern);
- }
- if (*s) { /* modifiers or commands? */
- for (s++; *s && index("Kharc",*s); s++) {
- if (*s == 'h') /* scan header */
- howmuch = 1;
- else if (*s == 'a') /* scan article */
- howmuch = 2;
- else if (*s == 'r') /* scan read articles */
- doread = TRUE;
- else if (*s == 'K') /* put into KILL file */
- saltaway = TRUE;
- else if (*s == 'c') /* make search case sensitive */
- foldcase = FALSE;
- }
- }
- while (isspace(*s) || *s == ':')
- s++;
- if (*s) {
- if (*s == 'm' || *s == 'M')
- doread = TRUE;
- if (*s == 'k') /* grandfather clause */
- *s = 'j';
- cmdlst = savestr(s);
- normal_return = SRCH_DONE;
- }
- art_howmuch = howmuch;
- art_doread = doread;
- if (srchahead)
- srchahead = -1;
- }
- else {
- register char *h;
-
- howmuch = 0; /* just search subjects */
- doread = (cmdchr == Ctl('p'));
- if (cmdchr == Ctl('n'))
- normal_return = SRCH_SUBJDONE;
- compex = &sub_compex;
- pattern = patbuf+1;
- strcpy(pattern,": *");
- h = pattern + strlen(pattern);
- interp(h,patbufsiz - (h-patbuf),"%\\s"); /* fetch current subject */
- if (cmdchr == 'K') {
- saltaway = TRUE;
- cmdchr = 'k';
- }
- if (cmdchr == 'k') {
- normal_return = SRCH_DONE;
- cmdlst = savestr("j");
- mark_as_read(); /* this article has this subject */
- if (!*h) {
- #ifdef VERBOSE
- IF(verbose) {
- fputs("\nCannot delete null subject.\n",stdout);
- FLUSH;
- }
- ELSE
- #endif
- #ifdef TERSE
- fputs("\nNull subject.\n",stdout) ; FLUSH;
- #endif
- return SRCH_ABORT;
- }
- #ifdef VERBOSE
- else if (verbose)
- printf("\nMarking subject \"%s\" as read.\n",h) ; FLUSH;
- #endif
- }
- else if (!srchahead)
- srchahead = -1;
- { /* compensate for notesfiles */
- register int i;
- for (i = 24; *h && i--; h++)
- if (*h == '\\')
- h++;
- *h = '\0';
- }
- #ifdef DEBUGGING
- if (debug) {
- printf("\npattern = %s\n",pattern) ; FLUSH;
- }
- #endif
- }
- if ((s = compile(compex,pattern,TRUE,foldcase)) != Nullch) {
- /* compile regular expression */
- printf("\n%s\n",s) ; FLUSH;
- return SRCH_ABORT;
- }
- #ifdef KILLFILES
- if (saltaway) {
- char saltbuf[LBUFLEN];
-
- s = saltbuf;
- sprintf(s,"/%s/",pattern);
- s += strlen(s);
- if (doread)
- *s++ = 'r';
- if (howmuch==1)
- *s++ = 'h';
- else if (howmuch==2)
- *s++ = 'a';
- *s++ = ':';
- if (!cmdlst)
- cmdlst = savestr("j");
- safecpy(s,cmdlst,LBUFLEN-(s-saltbuf));
- kf_append(saltbuf);
- }
- #endif
- if (cmdlst && index(cmdlst,'='))
- normal_return = SRCH_ERROR; /* listing subjects is an error? */
- if (get_cmd) {
- fputs("\nSearching...\n",stdout) ; FLUSH;
- /* give them something to read */
- }
- #ifdef USETHREADS
- if (mode == 't') {
- if (!cmdlst)
- cmdlst = savestr("+"); /* thread selector's default command */
- if (unread_selector)
- doread = TRUE;
- normal_return = SRCH_DONE;
- }
- #endif
- if (backward) {
- if (cmdlst && art <= lastart)
- art++; /* include current article */
- if (doread)
- check_first(absfirst);
- }
- else {
- if (art > lastart) {
- art = (doread ? absfirst : firstart);
- check_first(art--);
- }
- else if (cmdlst && art >= absfirst)
- art--; /* include current article */
- }
- if (srchahead > 0) {
- if (!backward)
- art = srchahead - 1;
- srchahead = -1;
- }
- assert(!cmdlst || *cmdlst);
- perform_cnt = 0;
- for (;;) {
- if (backward ?
- (--art < absfirst || (!doread && art < firstart)) :
- (++art > lastart)
- ) { /* out of articles? */
- if (cmdlst)
- free(cmdlst);
- return normal_return;
- }
- if (int_count) {
- int_count = 0;
- if (cmdlst)
- free(cmdlst);
- return SRCH_INTR;
- }
- /*NOSTRICT*/
- if (doread || !was_read(art)) {
- if (wanted(compex,art,howmuch)) {
- /* does the shoe fit? */
- if (cmdlst) {
- if (perform(cmdlst,TRUE)) {
- if (cmdlst)
- free(cmdlst);
- return SRCH_INTR;
- }
- }
- else {
- if (cmdlst)
- free(cmdlst);
- return SRCH_FOUND;
- }
- }
- else if (!cmdlst && ! (art%50)) {
- printf("...%ld",(long)art);
- fflush(stdout);
- }
- }
- }
- }
-
- /* determine if article fits pattern */
- /* returns TRUE if it exists and fits pattern, FALSE otherwise */
-
- bool
- wanted(compex, artnum, scope)
- COMPEX *compex;
- ART_NUM artnum;
- char_int scope;
- {
- if (!scope) {
- char subj_buf[266];
-
- #ifdef USETHREADS
- if (ThreadedGroup)
- {
- find_article(art);
- if (mode != 't')
- strcpy(subj_buf, "Subject: ");
- else
- *subj_buf = '\0';
- if (p_art && p_art->subject != -1) {
- if (!(p_art->flags & ROOT_ARTICLE))
- strcat(subj_buf,"Re: ");
- strcat(subj_buf,subject_ptrs[p_art->subject]);
- }
- }
- else
- #endif
- {
- strcpy(subj_buf, "Subject: ");
- strncpy(subj_buf+9,fetchsubj(artnum,FALSE,FALSE),256);
- }
- #ifdef DEBUGGING
- if (debug & DEB_SEARCH_AHEAD)
- printf("%s\n",subj_buf) ; FLUSH;
- #endif
- return execute(compex,subj_buf) != Nullch;
- }
- #ifdef CACHESUBJ
- else
- fetchsubj(artnum,FALSE,FALSE);/* might as well get subject handy */
- #endif
-
- #ifdef SERVER
- if (scope == 1){
- if (nntpopen(artnum,GET_HEADER) == Nullfp) /* we only need the header */
- return FALSE;
- }
- else
- #endif
- if (artopen(artnum) == Nullfp) /* ensure that article is open */
-
- return FALSE; /* if not, return NO MATCH */
- scope--;
- while (fgets(buf,LBUFLEN,artfp) != Nullch) {
- /* for each line of article */
- if (!scope && index(buf,':') == Nullch && *buf != ' ' && *buf != '\t')
- /* if headers only and out of header */
- return FALSE; /* say no go */
- if (execute(compex,buf) != Nullch) {
- /* does pattern matcher match? */
- return TRUE; /* say Eureka */
- }
- }
- return FALSE; /* out of article, so no match */
- }
- #endif
-
-