|
Packit |
f574b8 |
/*
|
|
Packit |
f574b8 |
* $LynxId: HTVMS_WaisProt.c,v 1.9 2010/09/24 23:51:22 tom Exp $
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
* HTVMS_WAISProt.c
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
* Adaptation for Lynx by F.Macrides (macrides@sci.wfeb.edu)
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
* 31-May-1994 FM Initial version.
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*
|
|
Packit |
f574b8 |
* Routines originally from WProt.c -- FM
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
/* WIDE AREA INFORMATION SERVER SOFTWARE:
|
|
Packit |
f574b8 |
* No guarantees or restrictions. See the readme file for the full standard
|
|
Packit |
f574b8 |
* disclaimer.
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
* 3.26.90 Harry Morris, morris@think.com
|
|
Packit |
f574b8 |
* 3.30.90 Harry Morris
|
|
Packit |
f574b8 |
* - removed chunk code from WAISSearchAPDU,
|
|
Packit |
f574b8 |
* - added makeWAISQueryType1Query() and readWAISType1Query() which replace
|
|
Packit |
f574b8 |
* makeWAISQueryTerms() and makeWAISQueryDocs().
|
|
Packit |
f574b8 |
* 4.11.90 HWM - generalized conditional includes (see c-dialect.h)
|
|
Packit |
f574b8 |
* - renamed makeWAISType1Query() to makeWAISTextQuery()
|
|
Packit |
f574b8 |
* renamed readWAISType1Query() to readWAISTextQuery()
|
|
Packit |
f574b8 |
* 5.29.90 TS - fixed bug in makeWAISQueryDocs
|
|
Packit |
f574b8 |
* added CSTFreeWAISFoo functions
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#define _C_WAIS_protocol_
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* This file implements the Z39.50 extensions required for WAIS
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#include <HTUtils.h>
|
|
Packit |
f574b8 |
#include <HTVMS_WaisUI.h>
|
|
Packit |
f574b8 |
#include <HTVMS_WaisProt.h>
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#include <LYLeaks.h>
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* very rough estimates of the size of an object */
|
|
Packit |
f574b8 |
#define DefWAISInitResponseSize (size_t)200
|
|
Packit |
f574b8 |
#define DefWAISSearchSize (size_t)3000
|
|
Packit |
f574b8 |
#define DefWAISSearchResponseSize (size_t)6000
|
|
Packit |
f574b8 |
#define DefWAISPresentSize (size_t)1000
|
|
Packit |
f574b8 |
#define DefWAISPresentResponseSize (size_t)6000
|
|
Packit |
f574b8 |
#define DefWAISDocHeaderSize (size_t)500
|
|
Packit |
f574b8 |
#define DefWAISShortHeaderSize (size_t)200
|
|
Packit |
f574b8 |
#define DefWAISLongHeaderSize (size_t)800
|
|
Packit |
f574b8 |
#define DefWAISDocTextSize (size_t)6000
|
|
Packit |
f574b8 |
#define DefWAISDocHeadlineSize (size_t)500
|
|
Packit |
f574b8 |
#define DefWAISDocCodeSize (size_t)500
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#define RESERVE_SPACE_FOR_WAIS_HEADER(len) \
|
|
Packit |
f574b8 |
if (*len > 0) \
|
|
Packit |
f574b8 |
*len -= header_len;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#define S_MALLOC(type) (type*)s_malloc(sizeof(type))
|
|
Packit |
f574b8 |
#define S_MALLOC2(type) (type*)s_malloc(sizeof(type) * 2)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
#define S_REALLOC2(type, ptr, num) (type*)s_realloc((char*)ptr, (sizeof(type) * (num + 2)))
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static unsigned long userInfoTagSize(data_tag tag,
|
|
Packit |
f574b8 |
unsigned long length)
|
|
Packit |
f574b8 |
/* return the number of bytes required to write the user info tag and
|
|
Packit |
f574b8 |
length
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* calculate bytes required to represent tag. max tag is 16K */
|
|
Packit |
f574b8 |
size = writtenCompressedIntSize(tag);
|
|
Packit |
f574b8 |
size += writtenCompressedIntSize(length);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (size);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static char *writeUserInfoHeader(data_tag tag,
|
|
Packit |
f574b8 |
long infoSize,
|
|
Packit |
f574b8 |
long estHeaderSize,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
/* write the tag and size, making sure the info fits. return the true end
|
|
Packit |
f574b8 |
of the info (after adjustment) note that the argument infoSize includes
|
|
Packit |
f574b8 |
estHeaderSize. Note that the argument len is the number of bytes remaining
|
|
Packit |
f574b8 |
in the buffer. Since we write the tag and size at the begining of the
|
|
Packit |
f574b8 |
buffer (in space that we reserved) we don't want to pass len the calls which
|
|
Packit |
f574b8 |
do that writing.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
long dummyLen = 100; /* plenty of space for a tag and size */
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
long realSize = infoSize - estHeaderSize;
|
|
Packit |
f574b8 |
long realHeaderSize = userInfoTagSize(tag, realSize);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (buffer == NULL || *len == 0)
|
|
Packit |
f574b8 |
return (NULL);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* write the tag */
|
|
Packit |
f574b8 |
buf = writeTag(tag, buf, &dummyLen);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* see if the if the header size was correct. if not,
|
|
Packit |
f574b8 |
we have to shift the info to fit the real header size */
|
|
Packit |
f574b8 |
if (estHeaderSize != realHeaderSize) { /* make sure there is enough space */
|
|
Packit |
f574b8 |
CHECK_FOR_SPACE_LEFT(realHeaderSize - estHeaderSize, len);
|
|
Packit |
f574b8 |
memmove(buffer + realHeaderSize, buffer + estHeaderSize, (size_t) (realSize));
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* write the size */
|
|
Packit |
f574b8 |
writeCompressedInteger(realSize, buf, &dummyLen);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* return the true end of buffer */
|
|
Packit |
f574b8 |
return (buffer + realHeaderSize + realSize);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static char *readUserInfoHeader(data_tag *tag,
|
|
Packit |
f574b8 |
unsigned long *num,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
/* read the tag and size */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readTag(tag, buf);
|
|
Packit |
f574b8 |
buf = readCompressedInteger(num, buf);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISInitResponse *makeWAISInitResponse(long chunkCode,
|
|
Packit |
f574b8 |
long chunkIDLen,
|
|
Packit |
f574b8 |
char *chunkMarker,
|
|
Packit |
f574b8 |
char *highlightMarker,
|
|
Packit |
f574b8 |
char *deHighlightMarker,
|
|
Packit |
f574b8 |
char *newLineChars)
|
|
Packit |
f574b8 |
/* create a WAIS init response object */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISInitResponse *init = S_MALLOC(WAISInitResponse);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
init->ChunkCode = chunkCode; /* note: none are copied! */
|
|
Packit |
f574b8 |
init->ChunkIDLength = chunkIDLen;
|
|
Packit |
f574b8 |
init->ChunkMarker = chunkMarker;
|
|
Packit |
f574b8 |
init->HighlightMarker = highlightMarker;
|
|
Packit |
f574b8 |
init->DeHighlightMarker = deHighlightMarker;
|
|
Packit |
f574b8 |
init->NewlineCharacters = newLineChars;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (init);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISInitResponse(WAISInitResponse *init)
|
|
Packit |
f574b8 |
/* free an object made with makeWAISInitResponse */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(init->ChunkMarker);
|
|
Packit |
f574b8 |
s_free(init->HighlightMarker);
|
|
Packit |
f574b8 |
s_free(init->DeHighlightMarker);
|
|
Packit |
f574b8 |
s_free(init->NewlineCharacters);
|
|
Packit |
f574b8 |
s_free(init);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeInitResponseInfo(InitResponseAPDU *init,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
/* write an init response object */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_UserInformationLength,
|
|
Packit |
f574b8 |
DefWAISInitResponseSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
WAISInitResponse *info = (WAISInitResponse *) init->UserInformationField;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeNum(info->ChunkCode, DT_ChunkCode, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(info->ChunkIDLength, DT_ChunkIDLength, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(info->ChunkMarker, DT_ChunkMarker, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(info->HighlightMarker, DT_HighlightMarker, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(info->DeHighlightMarker, DT_DeHighlightMarker, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(info->NewlineCharacters, DT_NewlineCharacters, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_UserInformationLength,
|
|
Packit |
f574b8 |
size,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readInitResponseInfo(void **info,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
/* read an init response object */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
long chunkCode, chunkIDLen;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
char *chunkMarker = NULL;
|
|
Packit |
f574b8 |
char *highlightMarker = NULL;
|
|
Packit |
f574b8 |
char *deHighlightMarker = NULL;
|
|
Packit |
f574b8 |
char *newLineChars = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
chunkCode = chunkIDLen = UNUSED;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_ChunkCode:
|
|
Packit |
f574b8 |
buf = readNum(&chunkCode, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_ChunkIDLength:
|
|
Packit |
f574b8 |
buf = readNum(&chunkIDLen, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_ChunkMarker:
|
|
Packit |
f574b8 |
buf = readString(&chunkMarker, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_HighlightMarker:
|
|
Packit |
f574b8 |
buf = readString(&highlightMarker, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DeHighlightMarker:
|
|
Packit |
f574b8 |
buf = readString(&deHighlightMarker, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_NewlineCharacters:
|
|
Packit |
f574b8 |
buf = readString(&newLineChars, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
s_free(highlightMarker);
|
|
Packit |
f574b8 |
s_free(deHighlightMarker);
|
|
Packit |
f574b8 |
s_free(newLineChars);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*info = (void *) makeWAISInitResponse(chunkCode, chunkIDLen, chunkMarker,
|
|
Packit |
f574b8 |
highlightMarker, deHighlightMarker,
|
|
Packit |
f574b8 |
newLineChars);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISSearch *makeWAISSearch(char *seedWords,
|
|
Packit |
f574b8 |
DocObj **docs,
|
|
Packit |
f574b8 |
char **textList,
|
|
Packit |
f574b8 |
long dateFactor,
|
|
Packit |
f574b8 |
char *beginDateRange,
|
|
Packit |
f574b8 |
char *endDateRange,
|
|
Packit |
f574b8 |
long maxDocsRetrieved)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* create a type 3 query object */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISSearch *query = S_MALLOC(WAISSearch);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
query->SeedWords = seedWords; /* not copied! */
|
|
Packit |
f574b8 |
query->Docs = docs; /* not copied! */
|
|
Packit |
f574b8 |
query->TextList = textList; /* not copied! */
|
|
Packit |
f574b8 |
query->DateFactor = dateFactor;
|
|
Packit |
f574b8 |
query->BeginDateRange = beginDateRange;
|
|
Packit |
f574b8 |
query->EndDateRange = endDateRange;
|
|
Packit |
f574b8 |
query->MaxDocumentsRetrieved = maxDocsRetrieved;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (query);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISSearch(WAISSearch *query)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* destroy an object made with makeWAISSearch() */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
void *ptr = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
s_free(query->SeedWords);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (query->Docs != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) query->Docs[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) query->Docs[++i])
|
|
Packit |
f574b8 |
freeDocObj((DocObj *) ptr);
|
|
Packit |
f574b8 |
s_free(query->Docs);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (query->TextList != NULL) /* XXX revisit when textlist is fully defined */
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) query->TextList[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) query->TextList[++i])
|
|
Packit |
f574b8 |
s_free(ptr);
|
|
Packit |
f574b8 |
s_free(query->TextList);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
s_free(query->BeginDateRange);
|
|
Packit |
f574b8 |
s_free(query->EndDateRange);
|
|
Packit |
f574b8 |
s_free(query);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
DocObj *makeDocObjUsingWholeDocument(any *docID,
|
|
Packit |
f574b8 |
char *type)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* construct a document object using byte chunks - only for use by
|
|
Packit |
f574b8 |
servers */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
DocObj *doc = S_MALLOC(DocObj);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doc->DocumentID = docID; /* not copied! */
|
|
Packit |
f574b8 |
doc->Type = type; /* not copied! */
|
|
Packit |
f574b8 |
doc->ChunkCode = CT_document;
|
|
Packit |
f574b8 |
return (doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
DocObj *makeDocObjUsingLines(any *docID,
|
|
Packit |
f574b8 |
char *type,
|
|
Packit |
f574b8 |
long start,
|
|
Packit |
f574b8 |
long end)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* construct a document object using line chunks - only for use by
|
|
Packit |
f574b8 |
servers */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
DocObj *doc = S_MALLOC(DocObj);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doc->ChunkCode = CT_line;
|
|
Packit |
f574b8 |
doc->DocumentID = docID; /* not copied */
|
|
Packit |
f574b8 |
doc->Type = type; /* not copied! */
|
|
Packit |
f574b8 |
doc->ChunkStart.Pos = start;
|
|
Packit |
f574b8 |
doc->ChunkEnd.Pos = end;
|
|
Packit |
f574b8 |
return (doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
DocObj *makeDocObjUsingBytes(any *docID,
|
|
Packit |
f574b8 |
char *type,
|
|
Packit |
f574b8 |
long start,
|
|
Packit |
f574b8 |
long end)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* construct a document object using byte chunks - only for use by
|
|
Packit |
f574b8 |
servers */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
DocObj *doc = S_MALLOC(DocObj);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doc->ChunkCode = CT_byte;
|
|
Packit |
f574b8 |
doc->DocumentID = docID; /* not copied */
|
|
Packit |
f574b8 |
doc->Type = type; /* not copied! */
|
|
Packit |
f574b8 |
doc->ChunkStart.Pos = start;
|
|
Packit |
f574b8 |
doc->ChunkEnd.Pos = end;
|
|
Packit |
f574b8 |
return (doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
DocObj *makeDocObjUsingParagraphs(any *docID,
|
|
Packit |
f574b8 |
char *type,
|
|
Packit |
f574b8 |
any *start,
|
|
Packit |
f574b8 |
any *end)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* construct a document object using byte chunks - only for use by
|
|
Packit |
f574b8 |
servers */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
DocObj *doc = S_MALLOC(DocObj);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doc->ChunkCode = CT_paragraph;
|
|
Packit |
f574b8 |
doc->DocumentID = docID; /* not copied */
|
|
Packit |
f574b8 |
doc->Type = type;
|
|
Packit |
f574b8 |
doc->ChunkStart.ID = start;
|
|
Packit |
f574b8 |
doc->ChunkEnd.ID = end;
|
|
Packit |
f574b8 |
return (doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeDocObj(DocObj *doc)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* free a docObj */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(doc->DocumentID);
|
|
Packit |
f574b8 |
s_free(doc->Type);
|
|
Packit |
f574b8 |
if (doc->ChunkCode == CT_paragraph) {
|
|
Packit |
f574b8 |
freeAny(doc->ChunkStart.ID);
|
|
Packit |
f574b8 |
freeAny(doc->ChunkEnd.ID);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
s_free(doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static char *writeDocObj(DocObj *doc,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* write as little as we can about the doc obj */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* we alwasy have to write the id, but its tag depends on if its a chunk */
|
|
Packit |
f574b8 |
if (doc->ChunkCode == CT_document)
|
|
Packit |
f574b8 |
buf = writeAny(doc->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
else
|
|
Packit |
f574b8 |
buf = writeAny(doc->DocumentID, DT_DocumentIDChunk, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (doc->Type != NULL)
|
|
Packit |
f574b8 |
buf = writeString(doc->Type, DT_TYPE, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (doc->ChunkCode) {
|
|
Packit |
f574b8 |
case CT_document:
|
|
Packit |
f574b8 |
/* do nothing - there is no chunk data */
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case CT_byte:
|
|
Packit |
f574b8 |
case CT_line:
|
|
Packit |
f574b8 |
buf = writeNum(doc->ChunkCode, DT_ChunkCode, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(doc->ChunkStart.Pos, DT_ChunkStartID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(doc->ChunkEnd.Pos, DT_ChunkEndID, buf, len);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case CT_paragraph:
|
|
Packit |
f574b8 |
buf = writeNum(doc->ChunkCode, DT_ChunkCode, buf, len);
|
|
Packit |
f574b8 |
buf = writeAny(doc->ChunkStart.ID, DT_ChunkStartID, buf, len);
|
|
Packit |
f574b8 |
buf = writeAny(doc->ChunkEnd.ID, DT_ChunkEndID, buf, len);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
panic("Implementation error: unknown chuck type %ld",
|
|
Packit |
f574b8 |
doc->ChunkCode);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static char *readDocObj(DocObj **doc,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* read whatever we have about the new document */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
data_tag tag;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*doc = S_MALLOC(DocObj);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
tag = peekTag(buf);
|
|
Packit |
f574b8 |
buf = readAny(&((*doc)->DocumentID), buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (tag == DT_DocumentID) {
|
|
Packit |
f574b8 |
(*doc)->ChunkCode = CT_document;
|
|
Packit |
f574b8 |
tag = peekTag(buf);
|
|
Packit |
f574b8 |
if (tag == DT_TYPE) /* XXX depends on DT_TYPE != what comes next */
|
|
Packit |
f574b8 |
buf = readString(&((*doc)->Type), buf);
|
|
Packit |
f574b8 |
/* ChunkStart and ChunkEnd are undefined */
|
|
Packit |
f574b8 |
} else if (tag == DT_DocumentIDChunk) {
|
|
Packit |
f574b8 |
boolean readParagraphs = false; /* for cleanup */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
tag = peekTag(buf);
|
|
Packit |
f574b8 |
if (tag == DT_TYPE) /* XXX depends on DT_TYPE != CT_FOO */
|
|
Packit |
f574b8 |
buf = readString(&((*doc)->Type), buf);
|
|
Packit |
f574b8 |
buf = readNum(&((*doc)->ChunkCode), buf);
|
|
Packit |
f574b8 |
switch ((*doc)->ChunkCode) {
|
|
Packit |
f574b8 |
case CT_byte:
|
|
Packit |
f574b8 |
case CT_line:
|
|
Packit |
f574b8 |
buf = readNum(&((*doc)->ChunkStart.Pos), buf);
|
|
Packit |
f574b8 |
buf = readNum(&((*doc)->ChunkEnd.Pos), buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case CT_paragraph:
|
|
Packit |
f574b8 |
buf = readAny(&((*doc)->ChunkStart.ID), buf);
|
|
Packit |
f574b8 |
buf = readAny(&((*doc)->ChunkEnd.ID), buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny((*doc)->DocumentID);
|
|
Packit |
f574b8 |
if (readParagraphs) {
|
|
Packit |
f574b8 |
freeAny((*doc)->ChunkStart.ID);
|
|
Packit |
f574b8 |
freeAny((*doc)->ChunkEnd.ID);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
s_free(doc);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
} else {
|
|
Packit |
f574b8 |
freeAny((*doc)->DocumentID);
|
|
Packit |
f574b8 |
s_free(*doc);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeSearchInfo(SearchAPDU *query,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* write out a WAIS query (type 1 or 3) */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
if (strcmp(query->QueryType, QT_TextRetrievalQuery) == 0) {
|
|
Packit |
f574b8 |
return (writeAny((any *) query->Query, DT_Query, buffer, len));
|
|
Packit |
f574b8 |
} else {
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_UserInformationLength,
|
|
Packit |
f574b8 |
DefWAISSearchSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
WAISSearch *info = (WAISSearch *) query->Query;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeString(info->SeedWords, DT_SeedWords, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->Docs != NULL) {
|
|
Packit |
f574b8 |
for (i = 0; info->Docs[i] != NULL; i++) {
|
|
Packit |
f574b8 |
buf = writeDocObj(info->Docs[i], buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* XXX text list */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeNum(info->DateFactor,
|
|
Packit |
f574b8 |
DT_DateFactor,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
buf = writeString(info->BeginDateRange,
|
|
Packit |
f574b8 |
DT_BeginDateRange,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
buf = writeString(info->EndDateRange,
|
|
Packit |
f574b8 |
DT_EndDateRange,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
buf = writeNum(info->MaxDocumentsRetrieved,
|
|
Packit |
f574b8 |
DT_MaxDocumentsRetrieved,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_UserInformationLength,
|
|
Packit |
f574b8 |
size,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readSearchInfo(void **info,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* read a WAIS query (type 1 or 3) */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
data_tag type = peekTag(buffer);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (type == DT_Query) /* this is a type 1 query */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
any *query = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readAny(&query, buf);
|
|
Packit |
f574b8 |
*info = (void *) query;
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
} else { /* a type 3 query */
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
char *seedWords = NULL;
|
|
Packit |
f574b8 |
char *beginDateRange = NULL;
|
|
Packit |
f574b8 |
char *endDateRange = NULL;
|
|
Packit |
f574b8 |
long dateFactor, maxDocsRetrieved;
|
|
Packit |
f574b8 |
char **textList = NULL;
|
|
Packit |
f574b8 |
DocObj **docIDs = NULL;
|
|
Packit |
f574b8 |
DocObj *doc = NULL;
|
|
Packit |
f574b8 |
long docs = 0;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
void *ptr = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
dateFactor = maxDocsRetrieved = UNUSED;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_SeedWords:
|
|
Packit |
f574b8 |
buf = readString(&seedWords, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
case DT_DocumentIDChunk:
|
|
Packit |
f574b8 |
if (docIDs == NULL) /* create a new doc list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
docIDs = S_MALLOC2(DocObj *);
|
|
Packit |
f574b8 |
} else { /* grow the doc list */
|
|
Packit |
f574b8 |
docIDs = S_REALLOC2(DocObj *, docIDs, docs);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readDocObj(&doc, buf);
|
|
Packit |
f574b8 |
if (buf == NULL) {
|
|
Packit |
f574b8 |
s_free(seedWords);
|
|
Packit |
f574b8 |
s_free(beginDateRange);
|
|
Packit |
f574b8 |
s_free(endDateRange);
|
|
Packit |
f574b8 |
if (docIDs != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) docIDs[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) docIDs[++i])
|
|
Packit |
f574b8 |
freeDocObj((DocObj *) ptr);
|
|
Packit |
f574b8 |
s_free(docIDs);
|
|
Packit |
f574b8 |
/* XXX should also free textlist when it is fully defined */
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
docIDs[docs++] = doc; /* put it in the list */
|
|
Packit |
f574b8 |
docIDs[docs] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_TextList:
|
|
Packit |
f574b8 |
/* XXX */
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DateFactor:
|
|
Packit |
f574b8 |
buf = readNum(&dateFactor, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_BeginDateRange:
|
|
Packit |
f574b8 |
buf = readString(&beginDateRange, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_EndDateRange:
|
|
Packit |
f574b8 |
buf = readString(&endDateRange, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_MaxDocumentsRetrieved:
|
|
Packit |
f574b8 |
buf = readNum(&maxDocsRetrieved, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
s_free(seedWords);
|
|
Packit |
f574b8 |
s_free(beginDateRange);
|
|
Packit |
f574b8 |
s_free(endDateRange);
|
|
Packit |
f574b8 |
if (docIDs != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) docIDs[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) docIDs[++i])
|
|
Packit |
f574b8 |
freeDocObj((DocObj *) ptr);
|
|
Packit |
f574b8 |
s_free(docIDs);
|
|
Packit |
f574b8 |
/* XXX should also free textlist when it is fully defined */
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*info = (void *) makeWAISSearch(seedWords, docIDs, textList,
|
|
Packit |
f574b8 |
dateFactor, beginDateRange, endDateRange,
|
|
Packit |
f574b8 |
maxDocsRetrieved);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentHeader *makeWAISDocumentHeader(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
long score,
|
|
Packit |
f574b8 |
long bestMatch,
|
|
Packit |
f574b8 |
long docLen,
|
|
Packit |
f574b8 |
long lines,
|
|
Packit |
f574b8 |
char **types,
|
|
Packit |
f574b8 |
char *source,
|
|
Packit |
f574b8 |
char *date,
|
|
Packit |
f574b8 |
char *headline,
|
|
Packit |
f574b8 |
char *originCity)
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* construct a standard document header, note that no fields are copied!
|
|
Packit |
f574b8 |
if the application needs to save these fields, it should copy them,
|
|
Packit |
f574b8 |
or set the field in this object to NULL before freeing it.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentHeader *header = S_MALLOC(WAISDocumentHeader);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
header->DocumentID = docID;
|
|
Packit |
f574b8 |
header->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
header->Score = score;
|
|
Packit |
f574b8 |
header->BestMatch = bestMatch;
|
|
Packit |
f574b8 |
header->DocumentLength = docLen;
|
|
Packit |
f574b8 |
header->Lines = lines;
|
|
Packit |
f574b8 |
header->Types = types;
|
|
Packit |
f574b8 |
header->Source = source;
|
|
Packit |
f574b8 |
header->Date = date;
|
|
Packit |
f574b8 |
header->Headline = headline;
|
|
Packit |
f574b8 |
header->OriginCity = originCity;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentHeader(WAISDocumentHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(header->DocumentID);
|
|
Packit |
f574b8 |
doList((void **) header->Types, fs_free); /* can't use the macro here ! */
|
|
Packit |
f574b8 |
s_free(header->Types);
|
|
Packit |
f574b8 |
s_free(header->Source);
|
|
Packit |
f574b8 |
s_free(header->Date);
|
|
Packit |
f574b8 |
s_free(header->Headline);
|
|
Packit |
f574b8 |
s_free(header->OriginCity);
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentHeader(WAISDocumentHeader *header, char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentHeaderGroup,
|
|
Packit |
f574b8 |
DefWAISDocHeaderSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size1;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(header->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Score, DT_Score, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->BestMatch, DT_BestMatch, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->DocumentLength, DT_DocumentLength, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Lines, DT_Lines, buf, len);
|
|
Packit |
f574b8 |
if (header->Types != NULL) {
|
|
Packit |
f574b8 |
long size;
|
|
Packit |
f574b8 |
char *ptr = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeTag(DT_TYPE_BLOCK, buf, len);
|
|
Packit |
f574b8 |
for (i = 0, size = 0, ptr = header->Types[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = header->Types[++i]) {
|
|
Packit |
f574b8 |
long typeSize = strlen(ptr);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
size += writtenTagSize(DT_TYPE);
|
|
Packit |
f574b8 |
size += writtenCompressedIntSize(typeSize);
|
|
Packit |
f574b8 |
size += typeSize;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = writeCompressedInteger((unsigned long) size, buf, len);
|
|
Packit |
f574b8 |
for (i = 0, ptr = header->Types[i]; ptr != NULL; ptr = header->Types[++i])
|
|
Packit |
f574b8 |
buf = writeString(ptr, DT_TYPE, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = writeString(header->Source, DT_Source, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->Date, DT_Date, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->Headline, DT_Headline, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->OriginCity, DT_OriginCity, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size1 = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentHeaderGroup,
|
|
Packit |
f574b8 |
size1,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentHeader(WAISDocumentHeader **header, char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size1;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID = NULL;
|
|
Packit |
f574b8 |
long versionNumber, score, bestMatch, docLength, lines;
|
|
Packit |
f574b8 |
char **types = NULL;
|
|
Packit |
f574b8 |
char *source = NULL;
|
|
Packit |
f574b8 |
char *date = NULL;
|
|
Packit |
f574b8 |
char *headline = NULL;
|
|
Packit |
f574b8 |
char *originCity = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
versionNumber = score = bestMatch = docLength = lines = UNUSED;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size1, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size1 + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Score:
|
|
Packit |
f574b8 |
buf = readNum(&score, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_BestMatch:
|
|
Packit |
f574b8 |
buf = readNum(&bestMatch, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentLength:
|
|
Packit |
f574b8 |
buf = readNum(&docLength, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Lines:
|
|
Packit |
f574b8 |
buf = readNum(&lines, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_TYPE_BLOCK:
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long size = -1;
|
|
Packit |
f574b8 |
long numTypes = 0;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readTag(&tag, buf);
|
|
Packit |
f574b8 |
buf = readCompressedInteger(&size, buf);
|
|
Packit |
f574b8 |
while (size > 0) {
|
|
Packit |
f574b8 |
char *type = NULL;
|
|
Packit |
f574b8 |
char *originalBuf = buf;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readString(&type, buf);
|
|
Packit |
f574b8 |
types = S_REALLOC2(char *, types, numTypes);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
types[numTypes++] = type;
|
|
Packit |
f574b8 |
types[numTypes] = NULL;
|
|
Packit |
f574b8 |
size -= (buf - originalBuf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
/* FALLTHRU */
|
|
Packit |
f574b8 |
case DT_Source:
|
|
Packit |
f574b8 |
buf = readString(&source, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Date:
|
|
Packit |
f574b8 |
buf = readString(&date, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Headline:
|
|
Packit |
f574b8 |
buf = readString(&headline, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_OriginCity:
|
|
Packit |
f574b8 |
buf = readString(&originCity, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
s_free(source);
|
|
Packit |
f574b8 |
s_free(date);
|
|
Packit |
f574b8 |
s_free(headline);
|
|
Packit |
f574b8 |
s_free(originCity);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*header = makeWAISDocumentHeader(docID, versionNumber, score, bestMatch,
|
|
Packit |
f574b8 |
docLength, lines, types, source, date, headline,
|
|
Packit |
f574b8 |
originCity);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentShortHeader *makeWAISDocumentShortHeader(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
long score,
|
|
Packit |
f574b8 |
long bestMatch,
|
|
Packit |
f574b8 |
long docLen,
|
|
Packit |
f574b8 |
long lines)
|
|
Packit |
f574b8 |
/* construct a short document header, note that no fields are copied!
|
|
Packit |
f574b8 |
if the application needs to save these fields, it should copy them,
|
|
Packit |
f574b8 |
or set the field in this object to NULL before freeing it.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentShortHeader *header = S_MALLOC(WAISDocumentShortHeader);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
header->DocumentID = docID;
|
|
Packit |
f574b8 |
header->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
header->Score = score;
|
|
Packit |
f574b8 |
header->BestMatch = bestMatch;
|
|
Packit |
f574b8 |
header->DocumentLength = docLen;
|
|
Packit |
f574b8 |
header->Lines = lines;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentShortHeader(WAISDocumentShortHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(header->DocumentID);
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentShortHeader(WAISDocumentShortHeader *header, char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentShortHeaderGroup,
|
|
Packit |
f574b8 |
DefWAISShortHeaderSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(header->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Score, DT_Score, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->BestMatch, DT_BestMatch, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->DocumentLength, DT_DocumentLength, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Lines, DT_Lines, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentShortHeaderGroup,
|
|
Packit |
f574b8 |
size,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentShortHeader(WAISDocumentShortHeader **header, char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID = NULL;
|
|
Packit |
f574b8 |
long versionNumber, score, bestMatch, docLength, lines;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
versionNumber = score = bestMatch = docLength = lines = UNUSED;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Score:
|
|
Packit |
f574b8 |
buf = readNum(&score, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_BestMatch:
|
|
Packit |
f574b8 |
buf = readNum(&bestMatch, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentLength:
|
|
Packit |
f574b8 |
buf = readNum(&docLength, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Lines:
|
|
Packit |
f574b8 |
buf = readNum(&lines, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*header = makeWAISDocumentShortHeader(docID, versionNumber, score, bestMatch,
|
|
Packit |
f574b8 |
docLength, lines);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentLongHeader *makeWAISDocumentLongHeader(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
long score,
|
|
Packit |
f574b8 |
long bestMatch,
|
|
Packit |
f574b8 |
long docLen,
|
|
Packit |
f574b8 |
long lines,
|
|
Packit |
f574b8 |
char **types,
|
|
Packit |
f574b8 |
char *source,
|
|
Packit |
f574b8 |
char *date,
|
|
Packit |
f574b8 |
char *headline,
|
|
Packit |
f574b8 |
char *originCity,
|
|
Packit |
f574b8 |
char *stockCodes,
|
|
Packit |
f574b8 |
char *companyCodes,
|
|
Packit |
f574b8 |
char *industryCodes)
|
|
Packit |
f574b8 |
/* construct a long document header, note that no fields are copied!
|
|
Packit |
f574b8 |
if the application needs to save these fields, it should copy them,
|
|
Packit |
f574b8 |
or set the field in this object to NULL before freeing it.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentLongHeader *header = S_MALLOC(WAISDocumentLongHeader);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
header->DocumentID = docID;
|
|
Packit |
f574b8 |
header->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
header->Score = score;
|
|
Packit |
f574b8 |
header->BestMatch = bestMatch;
|
|
Packit |
f574b8 |
header->DocumentLength = docLen;
|
|
Packit |
f574b8 |
header->Lines = lines;
|
|
Packit |
f574b8 |
header->Types = types;
|
|
Packit |
f574b8 |
header->Source = source;
|
|
Packit |
f574b8 |
header->Date = date;
|
|
Packit |
f574b8 |
header->Headline = headline;
|
|
Packit |
f574b8 |
header->OriginCity = originCity;
|
|
Packit |
f574b8 |
header->StockCodes = stockCodes;
|
|
Packit |
f574b8 |
header->CompanyCodes = companyCodes;
|
|
Packit |
f574b8 |
header->IndustryCodes = industryCodes;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentLongHeader(WAISDocumentLongHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(header->DocumentID);
|
|
Packit |
f574b8 |
doList((void **) header->Types, fs_free); /* can't use the macro here! */
|
|
Packit |
f574b8 |
s_free(header->Source);
|
|
Packit |
f574b8 |
s_free(header->Date);
|
|
Packit |
f574b8 |
s_free(header->Headline);
|
|
Packit |
f574b8 |
s_free(header->OriginCity);
|
|
Packit |
f574b8 |
s_free(header->StockCodes);
|
|
Packit |
f574b8 |
s_free(header->CompanyCodes);
|
|
Packit |
f574b8 |
s_free(header->IndustryCodes);
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentLongHeader(WAISDocumentLongHeader *header, char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentLongHeaderGroup,
|
|
Packit |
f574b8 |
DefWAISLongHeaderSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size1;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(header->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Score, DT_Score, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->BestMatch, DT_BestMatch, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->DocumentLength, DT_DocumentLength, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(header->Lines, DT_Lines, buf, len);
|
|
Packit |
f574b8 |
if (header->Types != NULL) {
|
|
Packit |
f574b8 |
long size;
|
|
Packit |
f574b8 |
char *ptr = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeTag(DT_TYPE_BLOCK, buf, len);
|
|
Packit |
f574b8 |
for (i = 0, size = 0, ptr = header->Types[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = header->Types[++i]) {
|
|
Packit |
f574b8 |
long typeSize = strlen(ptr);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
size += writtenTagSize(DT_TYPE);
|
|
Packit |
f574b8 |
size += writtenCompressedIntSize(typeSize);
|
|
Packit |
f574b8 |
size += typeSize;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = writeCompressedInteger((unsigned long) size, buf, len);
|
|
Packit |
f574b8 |
for (i = 0, ptr = header->Types[i]; ptr != NULL; ptr = header->Types[++i])
|
|
Packit |
f574b8 |
buf = writeString(ptr, DT_TYPE, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = writeString(header->Source, DT_Source, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->Date, DT_Date, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->Headline, DT_Headline, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->OriginCity, DT_OriginCity, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->StockCodes, DT_StockCodes, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->CompanyCodes, DT_CompanyCodes, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(header->IndustryCodes, DT_IndustryCodes, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size1 = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentLongHeaderGroup,
|
|
Packit |
f574b8 |
size1,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentLongHeader(WAISDocumentLongHeader **header, char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size1;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID;
|
|
Packit |
f574b8 |
long versionNumber, score, bestMatch, docLength, lines;
|
|
Packit |
f574b8 |
char **types;
|
|
Packit |
f574b8 |
char *source, *date, *headline, *originCity, *stockCodes, *companyCodes, *industryCodes;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docID = NULL;
|
|
Packit |
f574b8 |
versionNumber =
|
|
Packit |
f574b8 |
score =
|
|
Packit |
f574b8 |
bestMatch =
|
|
Packit |
f574b8 |
docLength =
|
|
Packit |
f574b8 |
lines = UNUSED;
|
|
Packit |
f574b8 |
types = NULL;
|
|
Packit |
f574b8 |
source =
|
|
Packit |
f574b8 |
date =
|
|
Packit |
f574b8 |
headline =
|
|
Packit |
f574b8 |
originCity =
|
|
Packit |
f574b8 |
stockCodes =
|
|
Packit |
f574b8 |
companyCodes =
|
|
Packit |
f574b8 |
industryCodes = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size1, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size1 + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Score:
|
|
Packit |
f574b8 |
buf = readNum(&score, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_BestMatch:
|
|
Packit |
f574b8 |
buf = readNum(&bestMatch, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentLength:
|
|
Packit |
f574b8 |
buf = readNum(&docLength, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Lines:
|
|
Packit |
f574b8 |
buf = readNum(&lines, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_TYPE_BLOCK:
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long size = -1;
|
|
Packit |
f574b8 |
long numTypes = 0;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readTag(&tag, buf);
|
|
Packit |
f574b8 |
readCompressedInteger(&size, buf);
|
|
Packit |
f574b8 |
while (size > 0) {
|
|
Packit |
f574b8 |
char *type = NULL;
|
|
Packit |
f574b8 |
char *originalBuf = buf;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readString(&type, buf);
|
|
Packit |
f574b8 |
types = S_REALLOC2(char *, types, numTypes);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
types[numTypes++] = type;
|
|
Packit |
f574b8 |
types[numTypes] = NULL;
|
|
Packit |
f574b8 |
size -= (buf - originalBuf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
/* FALLTHRU */
|
|
Packit |
f574b8 |
case DT_Source:
|
|
Packit |
f574b8 |
buf = readString(&source, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Date:
|
|
Packit |
f574b8 |
buf = readString(&date, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Headline:
|
|
Packit |
f574b8 |
buf = readString(&headline, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_OriginCity:
|
|
Packit |
f574b8 |
buf = readString(&originCity, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_StockCodes:
|
|
Packit |
f574b8 |
buf = readString(&stockCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_CompanyCodes:
|
|
Packit |
f574b8 |
buf = readString(&companyCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_IndustryCodes:
|
|
Packit |
f574b8 |
buf = readString(&industryCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
s_free(source);
|
|
Packit |
f574b8 |
s_free(date);
|
|
Packit |
f574b8 |
s_free(headline);
|
|
Packit |
f574b8 |
s_free(originCity);
|
|
Packit |
f574b8 |
s_free(stockCodes);
|
|
Packit |
f574b8 |
s_free(companyCodes);
|
|
Packit |
f574b8 |
s_free(industryCodes);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*header = makeWAISDocumentLongHeader(docID,
|
|
Packit |
f574b8 |
versionNumber,
|
|
Packit |
f574b8 |
score,
|
|
Packit |
f574b8 |
bestMatch,
|
|
Packit |
f574b8 |
docLength,
|
|
Packit |
f574b8 |
lines,
|
|
Packit |
f574b8 |
types,
|
|
Packit |
f574b8 |
source,
|
|
Packit |
f574b8 |
date,
|
|
Packit |
f574b8 |
headline,
|
|
Packit |
f574b8 |
originCity,
|
|
Packit |
f574b8 |
stockCodes,
|
|
Packit |
f574b8 |
companyCodes,
|
|
Packit |
f574b8 |
industryCodes);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISSearchResponse *
|
|
Packit |
f574b8 |
makeWAISSearchResponse(
|
|
Packit |
f574b8 |
char *seedWordsUsed,
|
|
Packit |
f574b8 |
WAISDocumentHeader **docHeaders,
|
|
Packit |
f574b8 |
WAISDocumentShortHeader **shortHeaders,
|
|
Packit |
f574b8 |
WAISDocumentLongHeader **longHeaders,
|
|
Packit |
f574b8 |
WAISDocumentText **text,
|
|
Packit |
f574b8 |
WAISDocumentHeadlines **headlines,
|
|
Packit |
f574b8 |
WAISDocumentCodes **codes,
|
|
Packit |
f574b8 |
diagnosticRecord ** diagnostics)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISSearchResponse *response = S_MALLOC(WAISSearchResponse);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
response->SeedWordsUsed = seedWordsUsed;
|
|
Packit |
f574b8 |
response->DocHeaders = docHeaders;
|
|
Packit |
f574b8 |
response->ShortHeaders = shortHeaders;
|
|
Packit |
f574b8 |
response->LongHeaders = longHeaders;
|
|
Packit |
f574b8 |
response->Text = text;
|
|
Packit |
f574b8 |
response->Headlines = headlines;
|
|
Packit |
f574b8 |
response->Codes = codes;
|
|
Packit |
f574b8 |
response->Diagnostics = diagnostics;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (response);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISSearchResponse(WAISSearchResponse * response)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
void *ptr = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
s_free(response->SeedWordsUsed);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->DocHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->DocHeaders[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->DocHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentHeader((WAISDocumentHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(response->DocHeaders);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->ShortHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->ShortHeaders[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->ShortHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentShortHeader((WAISDocumentShortHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(response->ShortHeaders);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->LongHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->LongHeaders[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->LongHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentLongHeader((WAISDocumentLongHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(response->LongHeaders);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->Text != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->Text[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->Text[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentText((WAISDocumentText *) ptr);
|
|
Packit |
f574b8 |
s_free(response->Text);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->Headlines != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->Headlines[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->Headlines[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentHeadlines((WAISDocumentHeadlines *) ptr);
|
|
Packit |
f574b8 |
s_free(response->Headlines);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->Codes != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->Codes[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->Codes[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentCodes((WAISDocumentCodes *) ptr);
|
|
Packit |
f574b8 |
s_free(response->Codes);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (response->Diagnostics != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) response->Diagnostics[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) response->Diagnostics[++i])
|
|
Packit |
f574b8 |
freeDiag((diagnosticRecord *) ptr);
|
|
Packit |
f574b8 |
s_free(response->Diagnostics);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
s_free(response);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeSearchResponseInfo(SearchResponseAPDU *query,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_UserInformationLength,
|
|
Packit |
f574b8 |
DefWAISSearchResponseSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
WAISSearchResponse *info = (WAISSearchResponse *) query->DatabaseDiagnosticRecords;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
void *header = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeString(info->SeedWordsUsed, DT_SeedWordsUsed, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* write out all the headers */
|
|
Packit |
f574b8 |
if (info->DocHeaders != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->DocHeaders[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->DocHeaders[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentHeader((WAISDocumentHeader *) header, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->ShortHeaders != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->ShortHeaders[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->ShortHeaders[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentShortHeader((WAISDocumentShortHeader *) header,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->LongHeaders != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->LongHeaders[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->LongHeaders[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentLongHeader((WAISDocumentLongHeader *) header,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->Text != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->Text[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->Text[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentText((WAISDocumentText *) header, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->Headlines != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->Headlines[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->Headlines[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentHeadlines((WAISDocumentHeadlines *) header,
|
|
Packit |
f574b8 |
buf,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->Codes != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->Codes[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->Codes[++i])
|
|
Packit |
f574b8 |
buf = writeWAISDocumentCodes((WAISDocumentCodes *) header, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (info->Diagnostics != NULL) {
|
|
Packit |
f574b8 |
for (i = 0, header = (void *) info->Diagnostics[i];
|
|
Packit |
f574b8 |
header != NULL;
|
|
Packit |
f574b8 |
header = (void *) info->Diagnostics[++i])
|
|
Packit |
f574b8 |
buf = writeDiag((diagnosticRecord *) header, buf, len);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_UserInformationLength,
|
|
Packit |
f574b8 |
size,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static void cleanUpWaisSearchResponse(char *buf,
|
|
Packit |
f574b8 |
char *seedWordsUsed,
|
|
Packit |
f574b8 |
WAISDocumentHeader **docHeaders,
|
|
Packit |
f574b8 |
WAISDocumentShortHeader **shortHeaders,
|
|
Packit |
f574b8 |
WAISDocumentLongHeader **longHeaders,
|
|
Packit |
f574b8 |
WAISDocumentText **text,
|
|
Packit |
f574b8 |
WAISDocumentHeadlines **headlines,
|
|
Packit |
f574b8 |
WAISDocumentCodes **codes,
|
|
Packit |
f574b8 |
diagnosticRecord ** diags)
|
|
Packit |
f574b8 |
/* if buf is NULL, we have just gotten a read error, and need to clean up
|
|
Packit |
f574b8 |
any state we have built. If not, then everything is going fine, and
|
|
Packit |
f574b8 |
we should just hang loose
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
void *ptr = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (buf == NULL) {
|
|
Packit |
f574b8 |
s_free(seedWordsUsed);
|
|
Packit |
f574b8 |
if (docHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) docHeaders[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) docHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentHeader((WAISDocumentHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(docHeaders);
|
|
Packit |
f574b8 |
if (shortHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) shortHeaders[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) shortHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentShortHeader((WAISDocumentShortHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(shortHeaders);
|
|
Packit |
f574b8 |
if (longHeaders != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) longHeaders[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) longHeaders[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentLongHeader((WAISDocumentLongHeader *) ptr);
|
|
Packit |
f574b8 |
s_free(longHeaders);
|
|
Packit |
f574b8 |
if (text != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) text[i];
|
|
Packit |
f574b8 |
ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) text[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentText((WAISDocumentText *) ptr);
|
|
Packit |
f574b8 |
s_free(text);
|
|
Packit |
f574b8 |
if (headlines != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) headlines[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) headlines[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentHeadlines((WAISDocumentHeadlines *) ptr);
|
|
Packit |
f574b8 |
s_free(headlines);
|
|
Packit |
f574b8 |
if (codes != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) codes[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) codes[++i])
|
|
Packit |
f574b8 |
freeWAISDocumentCodes((WAISDocumentCodes *) ptr);
|
|
Packit |
f574b8 |
s_free(codes);
|
|
Packit |
f574b8 |
if (diags != NULL)
|
|
Packit |
f574b8 |
for (i = 0, ptr = (void *) diags[i]; ptr != NULL;
|
|
Packit |
f574b8 |
ptr = (void *) diags[++i])
|
|
Packit |
f574b8 |
freeDiag((diagnosticRecord *) ptr);
|
|
Packit |
f574b8 |
s_free(diags);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readSearchResponseInfo(void **info,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
void *header = NULL;
|
|
Packit |
f574b8 |
WAISDocumentHeader **docHeaders = NULL;
|
|
Packit |
f574b8 |
WAISDocumentShortHeader **shortHeaders = NULL;
|
|
Packit |
f574b8 |
WAISDocumentLongHeader **longHeaders = NULL;
|
|
Packit |
f574b8 |
WAISDocumentText **text = NULL;
|
|
Packit |
f574b8 |
WAISDocumentHeadlines **headlines = NULL;
|
|
Packit |
f574b8 |
WAISDocumentCodes **codes = NULL;
|
|
Packit |
f574b8 |
long numDocHeaders, numLongHeaders, numShortHeaders, numText, numHeadlines;
|
|
Packit |
f574b8 |
long numCodes;
|
|
Packit |
f574b8 |
char *seedWordsUsed = NULL;
|
|
Packit |
f574b8 |
diagnosticRecord **diags = NULL;
|
|
Packit |
f574b8 |
diagnosticRecord *diag = NULL;
|
|
Packit |
f574b8 |
long numDiags = 0;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
numDocHeaders =
|
|
Packit |
f574b8 |
numLongHeaders =
|
|
Packit |
f574b8 |
numShortHeaders =
|
|
Packit |
f574b8 |
numText =
|
|
Packit |
f574b8 |
numHeadlines =
|
|
Packit |
f574b8 |
numCodes = 0;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_SeedWordsUsed:
|
|
Packit |
f574b8 |
buf = readString(&seedWordsUsed, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DatabaseDiagnosticRecords:
|
|
Packit |
f574b8 |
if (diags == NULL) /* create a new diag list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
diags = S_MALLOC2(diagnosticRecord *);
|
|
Packit |
f574b8 |
} else { /* grow the diag list */
|
|
Packit |
f574b8 |
diags = S_REALLOC2(diagnosticRecord *, diags, numDiags);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readDiag(&diag, buf);
|
|
Packit |
f574b8 |
diags[numDiags++] = diag; /* put it in the list */
|
|
Packit |
f574b8 |
diags[numDiags] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentHeaderGroup:
|
|
Packit |
f574b8 |
if (docHeaders == NULL) /* create a new header list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
docHeaders = S_MALLOC2(WAISDocumentHeader *);
|
|
Packit |
f574b8 |
} else { /* grow the doc list */
|
|
Packit |
f574b8 |
docHeaders = S_REALLOC2(WAISDocumentHeader *, docHeaders, numDocHeaders);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentHeader((WAISDocumentHeader **) &header, buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
docHeaders[numDocHeaders++] =
|
|
Packit |
f574b8 |
(WAISDocumentHeader *) header; /* put it in the list */
|
|
Packit |
f574b8 |
docHeaders[numDocHeaders] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentShortHeaderGroup:
|
|
Packit |
f574b8 |
if (shortHeaders == NULL) /* create a new header list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
shortHeaders = S_MALLOC2(WAISDocumentShortHeader *);
|
|
Packit |
f574b8 |
} else { /* grow the doc list */
|
|
Packit |
f574b8 |
shortHeaders = S_REALLOC2(WAISDocumentShortHeader *,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
numShortHeaders);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentShortHeader((WAISDocumentShortHeader **) &header,
|
|
Packit |
f574b8 |
buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
shortHeaders[numShortHeaders++] =
|
|
Packit |
f574b8 |
(WAISDocumentShortHeader *) header; /* put it in the list */
|
|
Packit |
f574b8 |
shortHeaders[numShortHeaders] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentLongHeaderGroup:
|
|
Packit |
f574b8 |
if (longHeaders == NULL) /* create a new header list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
longHeaders = S_MALLOC2(WAISDocumentLongHeader *);
|
|
Packit |
f574b8 |
} else { /* grow the doc list */
|
|
Packit |
f574b8 |
longHeaders = S_REALLOC2(WAISDocumentLongHeader *,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
numLongHeaders);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentLongHeader((WAISDocumentLongHeader **) &header,
|
|
Packit |
f574b8 |
buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
longHeaders[numLongHeaders++] =
|
|
Packit |
f574b8 |
(WAISDocumentLongHeader *) header; /* put it in the list */
|
|
Packit |
f574b8 |
longHeaders[numLongHeaders] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentTextGroup:
|
|
Packit |
f574b8 |
if (text == NULL) /* create a new list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
text = S_MALLOC2(WAISDocumentText *);
|
|
Packit |
f574b8 |
} else { /* grow the list */
|
|
Packit |
f574b8 |
text = S_REALLOC2(WAISDocumentText *, text, numText);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentText((WAISDocumentText **) &header, buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
text[numText++] =
|
|
Packit |
f574b8 |
(WAISDocumentText *) header; /* put it in the list */
|
|
Packit |
f574b8 |
text[numText] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentHeadlineGroup:
|
|
Packit |
f574b8 |
if (headlines == NULL) /* create a new list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
headlines = S_MALLOC2(WAISDocumentHeadlines *);
|
|
Packit |
f574b8 |
} else { /* grow the list */
|
|
Packit |
f574b8 |
headlines = S_REALLOC2(WAISDocumentHeadlines *, headlines, numHeadlines);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentHeadlines((WAISDocumentHeadlines **) &header,
|
|
Packit |
f574b8 |
buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
headlines[numHeadlines++] =
|
|
Packit |
f574b8 |
(WAISDocumentHeadlines *) header; /* put it in the list */
|
|
Packit |
f574b8 |
headlines[numHeadlines] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentCodeGroup:
|
|
Packit |
f574b8 |
if (codes == NULL) /* create a new list */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
codes = S_MALLOC2(WAISDocumentCodes *);
|
|
Packit |
f574b8 |
} else { /* grow the list */
|
|
Packit |
f574b8 |
codes = S_REALLOC2(WAISDocumentCodes *, codes, numCodes);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
buf = readWAISDocumentCodes((WAISDocumentCodes **) &header, buf);
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
RETURN_ON_NULL(buf);
|
|
Packit |
f574b8 |
codes[numCodes++] =
|
|
Packit |
f574b8 |
(WAISDocumentCodes *) header; /* put it in the list */
|
|
Packit |
f574b8 |
codes[numCodes] = NULL;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
cleanUpWaisSearchResponse(buf,
|
|
Packit |
f574b8 |
seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*info = (void *) makeWAISSearchResponse(seedWordsUsed,
|
|
Packit |
f574b8 |
docHeaders,
|
|
Packit |
f574b8 |
shortHeaders,
|
|
Packit |
f574b8 |
longHeaders,
|
|
Packit |
f574b8 |
text,
|
|
Packit |
f574b8 |
headlines,
|
|
Packit |
f574b8 |
codes,
|
|
Packit |
f574b8 |
diags);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentText *makeWAISDocumentText(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
any *documentText)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentText *docText = S_MALLOC(WAISDocumentText);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docText->DocumentID = docID;
|
|
Packit |
f574b8 |
docText->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
docText->DocumentText = documentText;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (docText);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentText(WAISDocumentText *docText)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(docText->DocumentID);
|
|
Packit |
f574b8 |
freeAny(docText->DocumentText);
|
|
Packit |
f574b8 |
s_free(docText);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentText(WAISDocumentText *docText, char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentTextGroup,
|
|
Packit |
f574b8 |
DefWAISDocTextSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(docText->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(docText->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeAny(docText->DocumentText, DT_DocumentText, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentTextGroup, size, header_len, buffer, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentText(WAISDocumentText **docText, char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID, *documentText;
|
|
Packit |
f574b8 |
long versionNumber;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docID = documentText = NULL;
|
|
Packit |
f574b8 |
versionNumber = UNUSED;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_DocumentText:
|
|
Packit |
f574b8 |
buf = readAny(&documentText, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
freeAny(documentText);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*docText = makeWAISDocumentText(docID, versionNumber, documentText);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentHeadlines *makeWAISDocumentHeadlines(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
char *source,
|
|
Packit |
f574b8 |
char *date,
|
|
Packit |
f574b8 |
char *headline,
|
|
Packit |
f574b8 |
char *originCity)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentHeadlines *docHeadline = S_MALLOC(WAISDocumentHeadlines);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docHeadline->DocumentID = docID;
|
|
Packit |
f574b8 |
docHeadline->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
docHeadline->Source = source;
|
|
Packit |
f574b8 |
docHeadline->Date = date;
|
|
Packit |
f574b8 |
docHeadline->Headline = headline;
|
|
Packit |
f574b8 |
docHeadline->OriginCity = originCity;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (docHeadline);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentHeadlines(WAISDocumentHeadlines *docHeadline)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(docHeadline->DocumentID);
|
|
Packit |
f574b8 |
s_free(docHeadline->Source);
|
|
Packit |
f574b8 |
s_free(docHeadline->Date);
|
|
Packit |
f574b8 |
s_free(docHeadline->Headline);
|
|
Packit |
f574b8 |
s_free(docHeadline->OriginCity);
|
|
Packit |
f574b8 |
s_free(docHeadline);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentHeadlines(WAISDocumentHeadlines *docHeadline, char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentHeadlineGroup,
|
|
Packit |
f574b8 |
DefWAISDocHeadlineSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(docHeadline->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(docHeadline->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docHeadline->Source, DT_Source, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docHeadline->Date, DT_Date, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docHeadline->Headline, DT_Headline, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docHeadline->OriginCity, DT_OriginCity, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentHeadlineGroup,
|
|
Packit |
f574b8 |
size,
|
|
Packit |
f574b8 |
header_len,
|
|
Packit |
f574b8 |
buffer,
|
|
Packit |
f574b8 |
len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentHeadlines(WAISDocumentHeadlines **docHeadline, char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID;
|
|
Packit |
f574b8 |
long versionNumber;
|
|
Packit |
f574b8 |
char *source, *date, *headline, *originCity;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docID = NULL;
|
|
Packit |
f574b8 |
versionNumber = UNUSED;
|
|
Packit |
f574b8 |
source = date = headline = originCity = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Source:
|
|
Packit |
f574b8 |
buf = readString(&source, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Date:
|
|
Packit |
f574b8 |
buf = readString(&date, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_Headline:
|
|
Packit |
f574b8 |
buf = readString(&headline, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_OriginCity:
|
|
Packit |
f574b8 |
buf = readString(&originCity, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
s_free(source);
|
|
Packit |
f574b8 |
s_free(date);
|
|
Packit |
f574b8 |
s_free(headline);
|
|
Packit |
f574b8 |
s_free(originCity);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*docHeadline = makeWAISDocumentHeadlines(docID, versionNumber, source, date,
|
|
Packit |
f574b8 |
headline, originCity);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
WAISDocumentCodes *makeWAISDocumentCodes(any *docID,
|
|
Packit |
f574b8 |
long versionNumber,
|
|
Packit |
f574b8 |
char *stockCodes,
|
|
Packit |
f574b8 |
char *companyCodes,
|
|
Packit |
f574b8 |
char *industryCodes)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
WAISDocumentCodes *docCodes = S_MALLOC(WAISDocumentCodes);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docCodes->DocumentID = docID;
|
|
Packit |
f574b8 |
docCodes->VersionNumber = versionNumber;
|
|
Packit |
f574b8 |
docCodes->StockCodes = stockCodes;
|
|
Packit |
f574b8 |
docCodes->CompanyCodes = companyCodes;
|
|
Packit |
f574b8 |
docCodes->IndustryCodes = industryCodes;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (docCodes);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void freeWAISDocumentCodes(WAISDocumentCodes *docCodes)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(docCodes->DocumentID);
|
|
Packit |
f574b8 |
s_free(docCodes->StockCodes);
|
|
Packit |
f574b8 |
s_free(docCodes->CompanyCodes);
|
|
Packit |
f574b8 |
s_free(docCodes->IndustryCodes);
|
|
Packit |
f574b8 |
s_free(docCodes);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writeWAISDocumentCodes(WAISDocumentCodes *docCodes,
|
|
Packit |
f574b8 |
char *buffer,
|
|
Packit |
f574b8 |
long *len)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
unsigned long header_len = userInfoTagSize(DT_DocumentCodeGroup,
|
|
Packit |
f574b8 |
DefWAISDocCodeSize);
|
|
Packit |
f574b8 |
char *buf = buffer + header_len;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
RESERVE_SPACE_FOR_WAIS_HEADER(len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = writeAny(docCodes->DocumentID, DT_DocumentID, buf, len);
|
|
Packit |
f574b8 |
buf = writeNum(docCodes->VersionNumber, DT_VersionNumber, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docCodes->StockCodes, DT_StockCodes, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docCodes->CompanyCodes, DT_CompanyCodes, buf, len);
|
|
Packit |
f574b8 |
buf = writeString(docCodes->IndustryCodes, DT_IndustryCodes, buf, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* now write the header and size */
|
|
Packit |
f574b8 |
size = buf - buffer;
|
|
Packit |
f574b8 |
buf = writeUserInfoHeader(DT_DocumentCodeGroup, size, header_len, buffer, len);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readWAISDocumentCodes(WAISDocumentCodes **docCodes,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char *buf = buffer;
|
|
Packit |
f574b8 |
unsigned long size;
|
|
Packit |
f574b8 |
unsigned long headerSize;
|
|
Packit |
f574b8 |
data_tag tag1;
|
|
Packit |
f574b8 |
any *docID;
|
|
Packit |
f574b8 |
long versionNumber;
|
|
Packit |
f574b8 |
char *stockCodes, *companyCodes, *industryCodes;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docID = NULL;
|
|
Packit |
f574b8 |
versionNumber = UNUSED;
|
|
Packit |
f574b8 |
stockCodes = companyCodes = industryCodes = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
buf = readUserInfoHeader(&tag1, &size, buf);
|
|
Packit |
f574b8 |
headerSize = buf - buffer;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
while (buf < (buffer + size + headerSize)) {
|
|
Packit |
f574b8 |
data_tag tag = peekTag(buf);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (tag) {
|
|
Packit |
f574b8 |
case DT_DocumentID:
|
|
Packit |
f574b8 |
buf = readAny(&docID, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_VersionNumber:
|
|
Packit |
f574b8 |
buf = readNum(&versionNumber, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_StockCodes:
|
|
Packit |
f574b8 |
buf = readString(&stockCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_CompanyCodes:
|
|
Packit |
f574b8 |
buf = readString(&companyCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case DT_IndustryCodes:
|
|
Packit |
f574b8 |
buf = readString(&industryCodes, buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
freeAny(docID);
|
|
Packit |
f574b8 |
s_free(stockCodes);
|
|
Packit |
f574b8 |
s_free(companyCodes);
|
|
Packit |
f574b8 |
s_free(industryCodes);
|
|
Packit |
f574b8 |
REPORT_READ_ERROR(buf);
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
*docCodes = makeWAISDocumentCodes(docID, versionNumber, stockCodes,
|
|
Packit |
f574b8 |
companyCodes, industryCodes);
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writePresentInfo(PresentAPDU * present GCC_UNUSED, char *buffer,
|
|
Packit |
f574b8 |
long *len GCC_UNUSED)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
/* The WAIS protocol doesn't use present info */
|
|
Packit |
f574b8 |
return (buffer);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readPresentInfo(void **info,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
/* The WAIS protocol doesn't use present info */
|
|
Packit |
f574b8 |
*info = NULL;
|
|
Packit |
f574b8 |
return (buffer);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *writePresentResponseInfo(PresentResponseAPDU * response GCC_UNUSED, char *buffer,
|
|
Packit |
f574b8 |
long *len GCC_UNUSED)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
/* The WAIS protocol doesn't use presentResponse info */
|
|
Packit |
f574b8 |
return (buffer);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
char *readPresentResponseInfo(void **info,
|
|
Packit |
f574b8 |
char *buffer)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
/* The WAIS protocol doesn't use presentResponse info */
|
|
Packit |
f574b8 |
*info = NULL;
|
|
Packit |
f574b8 |
return (buffer);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* support for type 1 queries */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* new use values (for the chunk types) */
|
|
Packit |
f574b8 |
#define BYTE "wb"
|
|
Packit |
f574b8 |
#define LINE "wl"
|
|
Packit |
f574b8 |
#define PARAGRAPH "wp"
|
|
Packit |
f574b8 |
#define DATA_TYPE "wt"
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* WAIS supports the following semantics for type 1 queries:
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
1. retrieve the header/codes from a document:
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
System_Control_Number = docID
|
|
Packit |
f574b8 |
Data Type = type (optional)
|
|
Packit |
f574b8 |
And
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
2. retrieve a fragment of the text of a document:
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
System_Control_Number = docID
|
|
Packit |
f574b8 |
Data Type = type (optional)
|
|
Packit |
f574b8 |
And
|
|
Packit |
f574b8 |
Chunk >= start
|
|
Packit |
f574b8 |
And
|
|
Packit |
f574b8 |
Chunk < end
|
|
Packit |
f574b8 |
And
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
Information from multiple documents may be requested by using
|
|
Packit |
f574b8 |
groups of the above joined by:
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
OR
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
( XXX does an OR come after every group but the first, or do they
|
|
Packit |
f574b8 |
all come at the end? )
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
( XXX return type could be in the element set)
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static query_term **makeWAISQueryTerms(DocObj **docs)
|
|
Packit |
f574b8 |
/* given a null terminated list of docObjs, construct the appropriate
|
|
Packit |
f574b8 |
query of the form given above
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
query_term **terms = NULL;
|
|
Packit |
f574b8 |
long numTerms = 0;
|
|
Packit |
f574b8 |
DocObj *doc = NULL;
|
|
Packit |
f574b8 |
long i;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (docs == NULL)
|
|
Packit |
f574b8 |
return ((query_term **) NULL);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms = (query_term **) s_malloc((size_t) (sizeof(query_term *) * 1));
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms[numTerms] = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* loop through the docs making terms for them all */
|
|
Packit |
f574b8 |
for (i = 0, doc = docs[i]; doc != NULL; doc = docs[++i]) {
|
|
Packit |
f574b8 |
any *type = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (doc->Type != NULL)
|
|
Packit |
f574b8 |
type = stringToAny(doc->Type);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (doc->ChunkCode == CT_document) /* a whole document */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
terms = S_REALLOC2(query_term *, terms, numTerms + 2);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(SYSTEM_CONTROL_NUMBER,
|
|
Packit |
f574b8 |
EQUAL, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
IGNORE, IGNORE, doc->DocumentID);
|
|
Packit |
f574b8 |
if (type != NULL) {
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(DATA_TYPE, EQUAL,
|
|
Packit |
f574b8 |
IGNORE, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
IGNORE, type);
|
|
Packit |
f574b8 |
terms[numTerms++] = makeOperatorTerm(AND);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
terms[numTerms] = NULL;
|
|
Packit |
f574b8 |
} else { /* a document fragment */
|
|
Packit |
f574b8 |
char chunk_att[ATTRIBUTE_SIZE];
|
|
Packit |
f574b8 |
any *startChunk = NULL;
|
|
Packit |
f574b8 |
any *endChunk = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms = S_REALLOC2(query_term *, terms, numTerms + 6);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
switch (doc->ChunkCode) {
|
|
Packit |
f574b8 |
case CT_byte:
|
|
Packit |
f574b8 |
case CT_line:
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char start[20], end[20];
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
(doc->ChunkCode == CT_byte) ?
|
|
Packit |
f574b8 |
StrNCpy(chunk_att, BYTE, ATTRIBUTE_SIZE) :
|
|
Packit |
f574b8 |
StrNCpy(chunk_att, LINE, ATTRIBUTE_SIZE);
|
|
Packit |
f574b8 |
sprintf(start, "%ld", doc->ChunkStart.Pos);
|
|
Packit |
f574b8 |
startChunk = stringToAny(start);
|
|
Packit |
f574b8 |
sprintf(end, "%ld", doc->ChunkEnd.Pos);
|
|
Packit |
f574b8 |
endChunk = stringToAny(end);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
case CT_paragraph:
|
|
Packit |
f574b8 |
StrNCpy(chunk_att, PARAGRAPH, ATTRIBUTE_SIZE);
|
|
Packit |
f574b8 |
startChunk = doc->ChunkStart.ID;
|
|
Packit |
f574b8 |
endChunk = doc->ChunkEnd.ID;
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
default:
|
|
Packit |
f574b8 |
/* error */
|
|
Packit |
f574b8 |
break;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(SYSTEM_CONTROL_NUMBER,
|
|
Packit |
f574b8 |
EQUAL, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
IGNORE,
|
|
Packit |
f574b8 |
IGNORE, doc->DocumentID);
|
|
Packit |
f574b8 |
if (type != NULL) {
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(DATA_TYPE, EQUAL, IGNORE,
|
|
Packit |
f574b8 |
IGNORE, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
type);
|
|
Packit |
f574b8 |
terms[numTerms++] = makeOperatorTerm(AND);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(chunk_att,
|
|
Packit |
f574b8 |
GREATER_THAN_OR_EQUAL,
|
|
Packit |
f574b8 |
IGNORE, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
IGNORE,
|
|
Packit |
f574b8 |
startChunk);
|
|
Packit |
f574b8 |
terms[numTerms++] = makeOperatorTerm(AND);
|
|
Packit |
f574b8 |
terms[numTerms++] = makeAttributeTerm(chunk_att, LESS_THAN,
|
|
Packit |
f574b8 |
IGNORE, IGNORE, IGNORE,
|
|
Packit |
f574b8 |
IGNORE,
|
|
Packit |
f574b8 |
endChunk);
|
|
Packit |
f574b8 |
terms[numTerms++] = makeOperatorTerm(AND);
|
|
Packit |
f574b8 |
terms[numTerms] = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (doc->ChunkCode == CT_byte || doc->ChunkCode == CT_line) {
|
|
Packit |
f574b8 |
freeAny(startChunk);
|
|
Packit |
f574b8 |
freeAny(endChunk);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
freeAny(type);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (i != 0) /* multiple independent queries, need a disjunction */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
terms = S_REALLOC2(query_term *, terms, numTerms);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms[numTerms++] = makeOperatorTerm(OR);
|
|
Packit |
f574b8 |
terms[numTerms] = NULL;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (terms);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
static DocObj **makeWAISQueryDocs(query_term **terms)
|
|
Packit |
f574b8 |
/* given a list of terms in the form given above, convert them to
|
|
Packit |
f574b8 |
DocObjs.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
query_term *docTerm = NULL;
|
|
Packit |
f574b8 |
query_term *fragmentTerm = NULL;
|
|
Packit |
f574b8 |
DocObj **docs = NULL;
|
|
Packit |
f574b8 |
DocObj *doc = NULL;
|
|
Packit |
f574b8 |
long docNum, termNum;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docNum = termNum = 0;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docs = S_MALLOC(DocObj *);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docs[docNum] = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* translate the terms into DocObjs */
|
|
Packit |
f574b8 |
while (true) {
|
|
Packit |
f574b8 |
query_term *typeTerm = NULL;
|
|
Packit |
f574b8 |
char *type = NULL;
|
|
Packit |
f574b8 |
long startTermOffset;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docTerm = terms[termNum];
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (docTerm == NULL)
|
|
Packit |
f574b8 |
break; /* we're done converting */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
typeTerm = terms[termNum + 1]; /* get the lead Term if it exists */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (strcmp(typeTerm->Use, DATA_TYPE) == 0) /* we do have a type */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
startTermOffset = 3;
|
|
Packit |
f574b8 |
type = anyToString(typeTerm->Term);
|
|
Packit |
f574b8 |
} else { /* no type */
|
|
Packit |
f574b8 |
startTermOffset = 1;
|
|
Packit |
f574b8 |
typeTerm = NULL;
|
|
Packit |
f574b8 |
type = NULL;
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* grow the doc list */
|
|
Packit |
f574b8 |
docs = S_REALLOC2(DocObj *, docs, docNum);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* figure out what kind of docObj to build - and build it */
|
|
Packit |
f574b8 |
fragmentTerm = terms[termNum + startTermOffset];
|
|
Packit |
f574b8 |
if (fragmentTerm != NULL && fragmentTerm->TermType == TT_Attribute) { /* build a document fragment */
|
|
Packit |
f574b8 |
query_term *startTerm = fragmentTerm;
|
|
Packit |
f574b8 |
query_term *endTerm = terms[termNum + startTermOffset + 2];
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (strcmp(startTerm->Use, BYTE) == 0) { /* a byte chunk */
|
|
Packit |
f574b8 |
doc = makeDocObjUsingBytes(duplicateAny(docTerm->Term),
|
|
Packit |
f574b8 |
type,
|
|
Packit |
f574b8 |
anyToLong(startTerm->Term),
|
|
Packit |
f574b8 |
anyToLong(endTerm->Term));
|
|
Packit |
f574b8 |
log_write("byte");
|
|
Packit |
f574b8 |
} else if (strcmp(startTerm->Use, LINE) == 0) { /* a line chunk */
|
|
Packit |
f574b8 |
doc = makeDocObjUsingLines(duplicateAny(docTerm->Term),
|
|
Packit |
f574b8 |
type,
|
|
Packit |
f574b8 |
anyToLong(startTerm->Term),
|
|
Packit |
f574b8 |
anyToLong(endTerm->Term));
|
|
Packit |
f574b8 |
log_write("line");
|
|
Packit |
f574b8 |
} else {
|
|
Packit |
f574b8 |
log_write("chunk"); /* a paragraph chunk */
|
|
Packit |
f574b8 |
doc = makeDocObjUsingParagraphs(duplicateAny(docTerm->Term),
|
|
Packit |
f574b8 |
type,
|
|
Packit |
f574b8 |
duplicateAny(startTerm->Term),
|
|
Packit |
f574b8 |
duplicateAny(endTerm->Term));
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
termNum += (startTermOffset + 4); /* point to next term */
|
|
Packit |
f574b8 |
} else { /* build a full document */
|
|
Packit |
f574b8 |
doc = makeDocObjUsingWholeDocument(duplicateAny(docTerm->Term),
|
|
Packit |
f574b8 |
type);
|
|
Packit |
f574b8 |
log_write("whole doc");
|
|
Packit |
f574b8 |
termNum += startTermOffset; /* point to next term */
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docs[docNum++] = doc; /* insert the new document */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
docs[docNum] = NULL; /* keep the doc list terminated */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (terms[termNum] != NULL)
|
|
Packit |
f574b8 |
termNum++; /* skip the OR operator it necessary */
|
|
Packit |
f574b8 |
else
|
|
Packit |
f574b8 |
break; /* we are done */
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (docs);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
any *makeWAISTextQuery(DocObj **docs)
|
|
Packit |
f574b8 |
/* given a list of DocObjs, return an any whose contents is the corresponding
|
|
Packit |
f574b8 |
type 1 query
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
any *buf = NULL;
|
|
Packit |
f574b8 |
query_term **terms = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms = makeWAISQueryTerms(docs);
|
|
Packit |
f574b8 |
buf = writeQuery(terms);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doList((void **) terms, freeTerm);
|
|
Packit |
f574b8 |
s_free(terms);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (buf);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
DocObj **readWAISTextQuery(any *buf)
|
|
Packit |
f574b8 |
/* given an any whose contents are type 1 queries of the WAIS sort,
|
|
Packit |
f574b8 |
construct a list of the corresponding DocObjs
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
query_term **terms = NULL;
|
|
Packit |
f574b8 |
DocObj **docs = NULL;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
terms = readQuery(buf);
|
|
Packit |
f574b8 |
docs = makeWAISQueryDocs(terms);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
doList((void **) terms, freeTerm);
|
|
Packit |
f574b8 |
s_free(terms);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
return (docs);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
/* Customized free WAIS object routines: */
|
|
Packit |
f574b8 |
/* */
|
|
Packit |
f574b8 |
/* This set of procedures is for applications to free a WAIS object */
|
|
Packit |
f574b8 |
/* which was made with makeWAISFOO. */
|
|
Packit |
f574b8 |
/* Each procedure frees only the memory that was allocated in its */
|
|
Packit |
f574b8 |
/* associated makeWAISFOO routine, thus it's not necessary for the */
|
|
Packit |
f574b8 |
/* caller to assign nulls to the pointer fields of the WAIS object. */
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISInitResponse(WAISInitResponse *init)
|
|
Packit |
f574b8 |
/* free an object made with makeWAISInitResponse */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(init);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISSearch(WAISSearch *query)
|
|
Packit |
f574b8 |
/* destroy an object made with makeWAISSearch() */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(query);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeDocObj(DocObj *doc)
|
|
Packit |
f574b8 |
/* free a docObj */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(doc);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocumentHeader(WAISDocumentHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocumentShortHeader(WAISDocumentShortHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocumentLongHeader(WAISDocumentLongHeader *header)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(header);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISSearchResponse(WAISSearchResponse * response)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(response);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocumentText(WAISDocumentText *docText)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(docText);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocHeadlines(WAISDocumentHeadlines *docHeadline)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(docHeadline);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISDocumentCodes(WAISDocumentCodes *docCodes)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
s_free(docCodes);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void CSTFreeWAISTextQuery(any *query)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
freeAny(query);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*
|
|
Packit |
f574b8 |
* Routines originally from WMessage.c -- FM
|
|
Packit |
f574b8 |
*
|
|
Packit |
f574b8 |
*----------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
/* WIDE AREA INFORMATION SERVER SOFTWARE
|
|
Packit |
f574b8 |
* No guarantees or restrictions. See the readme file for the full standard
|
|
Packit |
f574b8 |
* disclaimer.
|
|
Packit |
f574b8 |
* 3.26.90
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* This file is for reading and writing the wais packet header.
|
|
Packit |
f574b8 |
* Morris@think.com
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* to do:
|
|
Packit |
f574b8 |
* add check sum
|
|
Packit |
f574b8 |
* what do you do when checksum is wrong?
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*---------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void readWAISPacketHeader(char *msgBuffer,
|
|
Packit |
f574b8 |
WAISMessage * header_struct)
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
/* msgBuffer is a string containing at least HEADER_LENGTH bytes. */
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
memmove(header_struct->msg_len, msgBuffer, (size_t) 10);
|
|
Packit |
f574b8 |
header_struct->msg_type = char_downcase((unsigned long) msgBuffer[10]);
|
|
Packit |
f574b8 |
header_struct->hdr_vers = char_downcase((unsigned long) msgBuffer[11]);
|
|
Packit |
f574b8 |
memmove(header_struct->server, (void *) (msgBuffer + 12), (size_t) 10);
|
|
Packit |
f574b8 |
header_struct->compression = char_downcase((unsigned long) msgBuffer[22]);
|
|
Packit |
f574b8 |
header_struct->encoding = char_downcase((unsigned long) msgBuffer[23]);
|
|
Packit |
f574b8 |
header_struct->msg_checksum = char_downcase((unsigned long) msgBuffer[24]);
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*---------------------------------------------------------------------*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/* this modifies the header argument. See wais-message.h for the different
|
|
Packit |
f574b8 |
* options for the arguments.
|
|
Packit |
f574b8 |
*/
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
void writeWAISPacketHeader(char *header,
|
|
Packit |
f574b8 |
long dataLen,
|
|
Packit |
f574b8 |
long type,
|
|
Packit |
f574b8 |
char *server,
|
|
Packit |
f574b8 |
long compression,
|
|
Packit |
f574b8 |
long encoding,
|
|
Packit |
f574b8 |
long version)
|
|
Packit |
f574b8 |
/* Puts together the new wais before-the-z39-packet header. */
|
|
Packit |
f574b8 |
{
|
|
Packit |
f574b8 |
char lengthBuf[11];
|
|
Packit |
f574b8 |
char serverBuf[11];
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
long serverLen = strlen(server);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
if (serverLen > 10)
|
|
Packit |
f574b8 |
serverLen = 10;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
sprintf(lengthBuf, "%010ld", dataLen);
|
|
Packit |
f574b8 |
StrNCpy(header, lengthBuf, 10);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
header[10] = type & 0xFF;
|
|
Packit |
f574b8 |
header[11] = version & 0xFF;
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
StrNCpy(serverBuf, server, serverLen);
|
|
Packit |
f574b8 |
StrNCpy((char *) (header + 12), serverBuf, serverLen);
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
header[22] = compression & 0xFF;
|
|
Packit |
f574b8 |
header[23] = encoding & 0xFF;
|
|
Packit |
f574b8 |
header[24] = '0'; /* checkSum(header + HEADER_LENGTH,dataLen); XXX the result must be ascii */
|
|
Packit |
f574b8 |
}
|
|
Packit |
f574b8 |
|
|
Packit |
f574b8 |
/*---------------------------------------------------------------------*/
|