home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.muug.mb.ca
/
2014.06.ftp.muug.mb.ca.tar
/
ftp.muug.mb.ca
/
pub
/
src
/
gopher
/
gopher1.01
/
gopherd
/
index.c
< prev
next >
Wrap
C/C++ Source or Header
|
1992-06-22
|
9KB
|
419 lines
#include "gopherd.h"
#include <stdio.h>
#define WAISTYPE 1
#define NEXTTYPE 2
#define SHLLTYPE 3
#define GREPTYPE 4
void
Do_IndexTrans(sockfd, inputline)
int sockfd;
char *inputline;
{
char *IndexDirectory = NULL;
char *SearchString = NULL;
char *cp = NULL;
char *dbName = NULL;
char INDEXHost[256], INDEXPath[256]; /** Hard coded limits, ugh! **/
int INDEXPort=0;
char logline[256];
int Index_type=0;
/** First siphon off the directory pathname **/
IndexDirectory = inputline;
if (UsingHTML)
cp = strchr(inputline, '?');
else
cp = strchr(inputline, '\t');
if (cp == NULL) {
if (UsingHTML) {
Index_type = Find_index_type(IndexDirectory);
if (Index_type == -1) {
writestring(sockfd, "Server error....<P>\r\n");
writestring(sockfd, inputline);
writestring(sockfd, " is not a valid index<P>\r\n");
return;
}
writestring(sockfd, "<ISINDEX>\r\n");
writestring(sockfd, "This is a gopher index of ");
writestring(sockfd, inputline+1);
writestring(sockfd, ". <P>This is a ");
switch (Index_type) {
case WAISTYPE:
writestring(sockfd, "WAIS index\r\n");
break;
case NEXTTYPE:
writestring(sockfd, "NeXT Digital Librarian index\r\n");
break;
case GREPTYPE:
writestring(sockfd, "Brute force search of items in this directory\r\n");
break;
case SHLLTYPE:
writestring(sockfd, "strange gateway search\r\n");
break;
}
writestring(sockfd, "<P>\r\n");
return;
} else {
/** Give up it won't work..... **/
writestring(sockfd, ".\r\n");
return;
}
}
else
*cp = '\0';
/** And siphon off the search string **/
SearchString = cp +1;
/** Just in case, get rid of anything following a tab **/
cp = strchr(SearchString, '\t');
if (cp != NULL)
*cp = '\0';
Index_type = Find_index_type(IndexDirectory);
if (DEBUG)
printf("Index type is %d\n", Index_type);
if (Index_type < 0) {
/**** Error condition, unknown index type... ****/
Abortoutput(sockfd, "Unknown index type");
return;
}
if (Index_type == WAISTYPE) {
/*** The selector string has both the directory and the dbname... ***/
cp = strrchr(IndexDirectory, '/');
if (cp == NULL)
dbName = "index";
else {
dbName= cp+1;
*cp='\0';
}
}
if (Read_hostdata(IndexDirectory, INDEXHost, &INDEXPort, INDEXPath, dbName) <0) {
LOGGopher(sockfd, "Malformed hostdata file\n");
writestring(sockfd, "0Error on server, malformed hostdata\t\t\t1\r\n.\r\n");
return;
}
/* Doctor up the indexdirectory path if we're not running chroot()
* we use fixfile to keep things secure....
*/
if (!dochroot) {
IndexDirectory = fixfile(IndexDirectory);
cp = (char *) malloc(250);
strcpy(cp, Data_Dir);
strcat(cp, "/");
strcat(cp, IndexDirectory);
IndexDirectory = cp;
}
/** And call the appropriate query function **/
switch (Index_type) {
case NEXTTYPE:
NeXTIndexQuery(sockfd, SearchString, IndexDirectory, NULL,
INDEXHost, INDEXPort);
break;
case WAISTYPE:
WaisIndexQuery(sockfd, IndexDirectory, SearchString, dbName,
INDEXHost, INDEXPort, INDEXPath);
break;
case GREPTYPE:
GrepIndexQuery(sockfd, IndexDirectory, SearchString,
INDEXHost, INDEXPort, INDEXPath);
break;
case SHLLTYPE:
ShellIndexQuery(sockfd, IndexDirectory, SearchString);
break;
}
/** Log it here so we get the query in the logfile **/
if (dbName)
sprintf(logline, "search %s/%s for %s", IndexDirectory,
dbName, SearchString);
else
sprintf(logline, "search %s for %s", IndexDirectory, SearchString);
LOGGopher(sockfd, logline);
}
/*
* Try to figure out what each type of object is
*
* index types are
* Error == -1
* WAIS == 1
* NeXT == 2
* ShellScript == 3
* Grep == 4
*/
int
Find_index_type(gopherpath)
char *gopherpath;
{
char Teststr[512];
FILE *Testfile;
strcpy(Teststr, gopherpath);
strcat(Teststr, "/.index/index.ixif");
Testfile = rfopen(Teststr, "r");
if (Testfile != NULL) {
/*** Next Index ***/
fclose(Testfile);
return(NEXTTYPE);
}
strcpy(Teststr, gopherpath);
strcat(Teststr, ".inv");
Testfile = rfopen(Teststr, "r");
if (Testfile != NULL) {
/*** WAIS Index ***/
fclose(Testfile);
return(WAISTYPE);
}
strcpy(Teststr, gopherpath);
if (isadir(Teststr) == 1) {
return(GREPTYPE);
}
Testfile = rfopen(Teststr, "r");
if (Testfile != NULL) {
/** Shell script? **/
if (getc(Testfile) == '#')
if (getc(Testfile) == '!') {
fclose(Testfile);
return(SHLLTYPE);
}
}
return(-1);
}
/*
* Read in the data from a hostdata file...
*
* Try "<dbname>.hostdata" first, fall back to "hostdata" otherwise
*/
int
Read_hostdata(IndexDirectory, INDEXHost, INDEXPort, INDEXPath, dbName)
char *IndexDirectory;
char *INDEXHost, *INDEXPath;
int *INDEXPort;
char *dbName;
{
FILE *Hostfile;
char hostdataName[256];
/** Read in the proper hostdata file.... **/
rchdir(IndexDirectory); /** Change into the index directory **/
sprintf(hostdataName, "%s.hostdata", dbName); /* try idx.hostdata */
if ((Hostfile = ufopen(hostdataName, "r")) == NULL)
Hostfile = ufopen("hostdata", "r");
if (Hostfile == NULL) {
/*** Use the current host/port as the default ***/
fclose(Hostfile);
strcpy(INDEXHost, Zehostname);
*INDEXPort = GopherPort;
strcpy(INDEXPath, Data_Dir);
}
else {
char tempbuf[255];
if (fgets(INDEXHost, 64, Hostfile) == NULL)
return(-1);
ZapCRLF(INDEXHost);
if (fgets(tempbuf, 255, Hostfile) == NULL)
return(-1);
if ((*INDEXPort=atoi(tempbuf))==0)
return(-1);
if (fgets(INDEXPath, 256, Hostfile) == NULL)
return(-1);
ZapCRLF(INDEXPath);
fclose(Hostfile);
}
return(0);
}
/*
* This is a searching function that runs grep across files
* in a single directory...
*/
GrepIndexQuery(sockfd, Indexdir, Searchstr, INDEXHost, INDEXPort, INDEXPath)
int sockfd;
char *Indexdir;
char *Searchstr;
char *INDEXHost;
int INDEXPort;
char *INDEXPath;
{
FILE *moocow;
char command[512];
char inputline[512];
char outline[512];
char *cp;
GopherObj *gs;
GopherDirObj *gd;
gs = GSnew();
gd = GDnew(32);
sprintf(command, "egrep \"%s\" \"%s\"/*", Searchstr, Indexdir);
if (DEBUG)
printf("Grep command is %s\n", command);
moocow = popen(command, "r");
if (moocow == NULL) {
writestring(sockfd, ".\r\n");
LOGGopher(sockfd, "Couldn't open grep command");
return;
}
while (fgets(inputline, 512, moocow)) {
ZapCRLF(inputline);
GSsetType(gs, '0');
cp = strstr(inputline, INDEXPath) + strlen(INDEXPath);
GSsetTitle(gs, cp);
cp = strchr(inputline, ':');
*cp='\0';
cp =strstr(inputline, INDEXPath) + strlen(INDEXPath);
GSsetPath(gs, cp);
GSsetHost(gs, INDEXHost);
GSsetPort(gs, INDEXPort);
GDaddGS(gd, gs);
}
if (UsingHTML)
GDtoNetHTML(gd, sockfd);
else {
GDtoNet(gd, sockfd);
writestring(sockfd, ".\r\n");
}
pclose(moocow);
}
/*
* This starts up a shell script that's defined to be an index gateway
*
* The shell script should write out standard gopher directory protocol.
*/
ShellIndexQuery(sockfd, Script, Searchstring)
int sockfd;
char *Script;
char *Searchstring;
{
GopherDirObj *gd;
char Command[512];
FILE *Searchprocess;
char inputline[512];
gd = GDnew(32);
sprintf(Command, "\"%s\" \"%s\"", Script, Searchstring);
Searchprocess = popen(Command, "r");
if (Searchprocess == NULL) {
writestring(sockfd, ".\r\n");
return;
}
GDfromNet(gd, fileno(Searchprocess), NULL);
if (UsingHTML)
GDtoNetHTML(gd, sockfd);
else {
GDtoNet(gd, sockfd);
writestring(sockfd, ".\r\n");
}
pclose(Searchprocess);
GDdestroy(gd);
}
#ifndef WAISSEARCH
void
WaisIndexQuery(sockfd, index_directory, SearchWords, new_db_name, INDEXHost, INDEXPort, INDEXPath)
int sockfd;
char *index_directory;
char *SearchWords;
char *new_db_name;
char *INDEXHost;
int INDEXPort;
char *INDEXPath;
{
Abortoutput(sockfd, "Sorry, this isn't a WAIS index...");
return;
}
#endif
#ifndef NEXTSEARCH
void
NeXTIndexQuery(sockfd, SearchWords, ZIndexDirectory, DatabaseNm, INDEXHost, INDEXPort)
int sockfd;
char *SearchWords;
char *ZIndexDirectory;
char *DatabaseNm; /*** Not used by the next indexer... ***/
char *INDEXHost;
int INDEXPort;
{
Abortoutput(sockfd, "This isn't a NeXT... is it?");
return;
}
#endif