home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 10 Tools
/
10-Tools.zip
/
samtexco.zip
/
imlsmp02.c
< prev
next >
Wrap
Text File
|
2000-03-31
|
159KB
|
2,612 lines
/*====================================================================*/
/* */
/* IBM Text Search API Sample Application Program */
/* */
/*====================================================================*/
/* */
/* Name: IMLSMP02.C */
/* ----- */
/* */
/* COPYRIGHT: */
/* ---------- */
/* Digital Library Version 2 - 5648-A08. */
/* (C) Copyright IBM Corp. 1996. */
/* All Rights Reserved */
/* US Government Users Restricted Rights */
/* Use, duplication or disclosure restricted */
/* by GSA ADP Schedule */
/* Contract with IBM Corp. */
/* Licensed Materials - Property of IBM */
/* */
/* DISCLAIMER OF WARRANTIES: */
/* ------------------------- */
/* The following [enclosed] code is sample code created by IBM */
/* Corporation. This sample code is not part of any standard IBM */
/* product and is provided to you solely for the purpose of */
/* assisting you in the development of your applications. */
/* The code is provided "AS IS", without warranty of any kind. */
/* IBM shall not be liable for any damages arising out of your */
/* use of the sample code, even if they have been advised of the */
/* possibility of such damages. */
/* */
/*====================================================================*/
/*====================================================================*/
/* IMLSMP02.c (API Sample Application Program 2) */
/*====================================================================*/
/*=====================================================================+
| |
| Title: IBM Text Search Sample Application Program |
| |
| Purpose: Template for a C application program that uses the |
| IBM Text Search Application Program Interface. |
| |
| The IBM Text Search Sample Application Program |
| has to be considered as an appendix document to the |
| IBM Text Search Application Program Interface |
| Guide and Reference (SH12-6317-00) |
| rather than as a complete application to be run on |
| your work station. |
| |
| The program shows |
| - the natural sequence of API function calls |
| during cross-index search |
| - the natural sequence of API function calls |
| if the result should be ranked |
| - how to intercept the API function return codes |
| - how to build datastream input for API functions |
| - how to parse datastream output from API functions |
| - how to use the macros VAL2 and ID |
| |
| Operation: - Builds a server list containing all Text Search |
| servers that can be connected to the application |
| - Starts a session with one of the servers from the |
| server list |
| - Lists all information retrieval indexes that |
| can be accessed from the current session in an |
| index table |
| - Opens the first three indexes contained in the |
| index table and adds corresponding index |
| information to the index table |
| - Builds a query datastream with option RANK and |
| issues a search request. |
| - If there are documents found: |
| - Ranks the result |
| - Obtains the result information and anchors it |
| in the index table structure |
| - Selects the result for just one index |
| - Sorts the result according to the rank value |
| in descending order |
| - Deletes the search result lists |
| - Deletes the current search result |
| - Deletes the index group |
| - Closes all current information-retrieval indexes |
| - Ends the current information-retrieval session |
| |
| API function calls: |
| |
| EhwListServers |
| EhwStartSession |
| EhwListIndexes |
| EhwOpenIndex |
| EhwGetIndexInfo |
| EhwCreateIndexGroup |
| EhwSearch |
| EhwGetProblemInfo |
| EhwRank |
| EhwCreateResultList |
| EhwGetResultList |
| EhwSelectResultList |
| EhwSort |
| EhwDeleteResult |
| EhwDeleteIndexGroup |
| EhwCloseIndex |
| EhwEndSession |
| |
| Notes: The program is designed to handle parallel |
| sessions with multiple open indexes. |
| |
| Dependencies: |
| |
| |
+=====================================================================*/
/*=====================================================================+
| |
| Entry point: main |
| |
| Function: Demonstrates how a C application program can use the |
| IBM Text Search Application Program Interface. |
| Input |
| parameters: None |
| |
| Output |
| parameters: None |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| Calls: Internal functions: |
| |
| WriteDataStream |
| ListServers |
| ListIndexes |
| OpenIndex |
| GetProblemInfo |
| ListResult |
| DeleteResults |
| HandleExit |
| |
| API functions: |
| |
| EhwStartSession |
| EhwCreateIndexGroup |
| EhwSearch |
| EhwRank |
| EhwCreateResultList |
| EhwSelectResultList |
| EhwSort |
| EhwDeleteIndexGroup |
| EhwDeleteResult |
| EhwCloseIndex |
| EhwEndSession |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Allocate a work area used to hold API datastreams. |
| |
| - Call the internal function ListServers to build a server list |
| containing all Text Search servers that can be connected to |
| the application. |
| - Check the function status code. |
| |
| - Select one server name from the server table. |
| - Write the session information datastream to a work area using |
| the internal function WriteDataItem. |
| - Invoke the API function EhwStartSession to connect |
| to the selected server and to start a session. |
| - Check the API function return code. |
| |
| - Call the internal function ListIndexes to build an index table |
| and to create index information for any index entry. |
| - Check the function status code. |
| |
| - Select index names from the index table. |
| - Invoke the internal function OpenIndex to open the selected |
| indexes and to complete the index information for each index. |
| - Check the function status code. |
| |
| - Build a query datastream using function WriteDataItem. |
| - Issue an EhwSearch API function call to process the query. |
| - Check the API function return code. |
| |
| - If the result size is greater than zero |
| - Call API function EhwCreateResultList to get a handle |
| of the result object. |
| - Check the function return code. |
| - Call API function EhwRank to rank the result list. |
| - Check the function return code. |
| - Call the internal function ListResult to build the |
| result information for the current ranked result list |
| and to anchor it in the index list. |
| - Check the function status code. |
| - Reduce your view of the result list: |
| select result information for the first index only by |
| calling API function EhwSelectResultList. |
| - Check the function return code. |
| - Sort this result list by rank value in descending order: |
| call API function EhwSort. |
| - Check the function return code. |
| - Call the internal function ListResult to get the |
| sorted result list. |
| - Check the function status code. |
| |
| To end search processing: |
| |
| - Invoke the internal function DeleteResults to release |
| the result information. |
| - Check the function status code. |
| |
| - Issue an EhwDeleteIndexGroup function call to delete |
| the index group. |
| - Check the API function return code. |
| - Close all open indexes by calling API function EhwCloseIndex. |
| |
| - Issue an EhwEndSession function call to end the current session. |
| - Check the API function return code. |
| |
| - Terminate search processing by calling the internal function |
| HandleExit where allocated memory is freed. |
| |
| - Return to the caller. |
| |
+=====================================================================*/
#if defined (__WINDOWS__)
#include <windows.h>
#define __WINDOWS_H 1
#endif
/*--------------------------------------------------------------------*/
/* external definitions */
/*--------------------------------------------------------------------*/
#include <stdio.h> /* => printf () */
#include <stdlib.h> /* standard library functions */
#include <string.h> /* string handling functions */
#include <imoapic.h> /* API definitions for C */
#if defined (__UNIX__)
#include "ehwlsgvi.h"
#include <time.h>
#endif
/*--------------------------------------------------------------------*/
/* internal definitions */
/*--------------------------------------------------------------------*/
#include <imlsmp02.h> /* API sample definitions */
#ifdef __cplusplus
extern "C"
{
#endif
#ifdef __cplusplus
}
#endif
/*====================================================================*/
/* main function (IMLSMP02.c) */
/*====================================================================*/
INT main /* Sample Application Program */
(
INT argc, PCHAR argv[], PCHAR envp[]
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulIndexHandle = 0L; /* API index handle */
ULONG ulGroupHandle = 0L; /* API index group handle */
ULONG ulResultHandle = 0L; /* API result handle */
ULONG ulResultHandle2 = 0L; /* API result handle from */
/* EhwCreateResultList */
ULONG ulResultHandle3 = 0L; /* API result handle from */
/* EhwSelectResultList */
ULONG ulResultSize = 0L; /* API result size */
ULONG ulResListSize = 0L; /* API result list size */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PVOID pSession = NULL; /* API session pointer */
USHORT usValue = 0; /* USHORT datastream value */
USHORT iCount = 0; /* loop variable */
INT iStatus = RC_TRUE;/* WriteDataItem() status code */
PCHAR pArea = NULL; /* pointer to work area */
PSRVTBL pServerTable = NULL; /* pointer to server table */
PSERVER pServer = NULL; /* server table entry pointer */
PXTBL pIndexTable = NULL; /* pointer to index table */
PHTBL pGroupTable = NULL; /* pointer to index group table*/
PPINDEX ppIndex = NULL; /* ptr to index info. pointer */
PINDEX pIndex[10]; /* index information pointer */
ULONG *pulIndexHandle = NULL; /* API index handle */
PCHAR pIndexName = NULL;
PPBLTBL pIndexProblem = NULL;
USHORT IndexNameLen;
UCHAR attribute;
CHAR work[20];
UCHAR word1[50];
UCHAR word2[50];
/*-----------------------------------------------------------------*/
/* initialization / processing */
/*-----------------------------------------------------------------*/
memset(pIndex, 0x00, sizeof(pIndex));
memset(work, 0x00, sizeof(work));
memset(word1, 0x00, sizeof(word1));
memset(word2, 0x00, sizeof(word2));
//---------------------------------------------------------
// only words entered in the cmd line are searched for
//---------------------------------------------------------
if(argc >1)
strcpy(word1, argv[1]);
else
strcpy(word1, QUERY_WORD01);
if(argc >2)
strcpy(word2, argv[2]);
else
strcpy(word2, QUERY_WORD02);
printf( " search term1 = %s \n", word1);
printf( " search term2 = %s \n", word2);
/*-----------------------------------------------------------------*/
/* allocate a work area to hold datastream information */
/*-----------------------------------------------------------------*/
pArea = malloc(SIZEOF_DATA_AREA); /* allocate the work area */
if (!pArea) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* end if allocation failed */
/*-----------------------------------------------------------------*/
/* get a list of all SM servers that are known on your client */
/* call function ListServers to build a server table */
/*-----------------------------------------------------------------*/
iStatus = ListServers (&pServerTable);
if (iStatus != RC_TRUE) /* check ListServers status */
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
free(pArea); /* release the work area */
return (iStatus); /* return to the caller */
} /* endif ListServers failed */
/*-----------------------------------------------------------------*/
/* select an information-retrieval server: */
/* - either the first server of the server table that complies */
/* with the server location specification (SESSION_IRSL) */
/* - or the last server of the server table */
/*-----------------------------------------------------------------*/
pServer = pServerTable->Server; /* set server table entry ptr */
for (iCount = (pServerTable->usServerCount) - 1; iCount > 0; iCount--)
{
if (pServer->Location == SESSION_IRSL) break;
pServer = (PSERVER )((PCHAR )pServer + (offsetof(SERV, Name[0])
+ pServer->usNameLength));
}
/*-----------------------------------------------------------------*/
/* write the session information datastream to the work area */
/*-----------------------------------------------------------------*/
ulDataLength = SIZEOF_DATA_AREA; /* initialize remaining length */
pDataStream = pArea; /* initialize target pointer */
/* write IRSN item */
iStatus = WriteDataItem (ID_IRSN, IT_ATOMIC,
pServer->usNameLength,
(PCHAR )pServer->Name,
&ulDataLength, &pDataStream);
if (iStatus != RC_TRUE) /* check WriteDataItem status */
{ /* area is too small to hold */
/* the session information */
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
free(pServerTable); /* release the server table */
free(pArea); /* release the work area */
return (iStatus); /* return to the caller */
}
/* set length of session info. */
ulDataLength = (ULONG )(pDataStream - pArea);
pDataStream = pArea; /* set pointer to datastream */
memcpy(work, pServer->Name, pServer->usNameLength);
/*-----------------------------------------------------------------*/
/* Start a session, using API service EhwStartSession */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwStartSession (ulDataLength, /* In -- datastream length */
pDataStream, /* In -- session information */
&pSession, /* Out -- session pointer */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwStartSession) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
free(pServerTable); /* release the server table */
free(pArea); /* release the work area */
printf("Start Session failed for Text Search server %s \n", work);
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
printf("Start Session successful for Text Search server %s \n", work);
/*-----------------------------------------------------------------*/
/* save the session pointer in the current server information */
/*-----------------------------------------------------------------*/
pServer->pSession = pSession;
/*-----------------------------------------------------------------*/
/* create an index table that holds the accessible information of */
/* retrieval indexes (at most LT_NUMBER_OF_INDEXES entries) by */
/* invoking the function ListIndexes */
/*-----------------------------------------------------------------*/
iStatus = ListIndexes (pSession, /* In -- session pointer */
&pIndexTable /* In/Out index table pointer */
);
if (iStatus != RC_TRUE) /* check ListServers status */
{ /* server table is not built */
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
} /* endif ListIndexes failed */
/*-----------------------------------------------------------------*/
/* save the index table in the current server information */
/*-----------------------------------------------------------------*/
pServer->pIndexTable = pIndexTable;
/*-----------------------------------------------------------------*/
/* create an index group table for LT_NUMBER_OF_INDEXES entries */
/* (LT_NUMBER_OF_INDEXES must be greater than zero ) */
/*-----------------------------------------------------------------*/
ulDataLength = (offsetof(HTBL, ulHandle[0]) +
LT_NUMBER_OF_INDEXES * sizeof(pGroupTable->ulHandle));
pGroupTable = (PHTBL )malloc((size_t )ulDataLength);
if (!pGroupTable) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/* write the header text */
/*-----------------------------------------------------------------*/
/* save the index group table in the current server information */
/*-----------------------------------------------------------------*/
pServer->pGroupTable = pGroupTable;
memcpy(pGroupTable->Header,
"GroupTbl", sizeof(pGroupTable->Header));
/* set the index table length */
pGroupTable->ulTableLength = ulDataLength;
/* init. the number of slots */
pGroupTable->usHandleSlots = LT_NUMBER_OF_INDEXES;
pGroupTable->usHandleCount = 0; /* init. the number of entries */
/* set the table entry pointer */
pulIndexHandle = pGroupTable->ulHandle;/* to the first index entry */
/*-----------------------------------------------------------------*/
/* select the first three index information entries in the index */
/* table in order to build an IndexGroup on which to search */
/*-----------------------------------------------------------------*/
iCount = pIndexTable->usIndexCount;
for(iCount = 0; iCount < pIndexTable->usIndexCount; iCount++ )
{
ppIndex = &pIndexTable->pIndex[iCount];/* access index info */
/*---------------------------------------------------------------*/
/* open the specified index, complete its information structure: */
/* invoke internal function OpenIndex */
/*---------------------------------------------------------------*/
iStatus = OpenIndex (pSession, /* In -- session pointer */
ppIndex); /* In/Out index info. (ptr) */
if (iStatus != RC_TRUE) /* check OpenIndex status */
{ /* index info. is not modified */
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
} /* endif OpenIndex failed */
memset(work, 0x00, sizeof(work));
memcpy(work, (PCHAR ) (*ppIndex)->pName->value, 8 );
printf( " index opened successfully = %s \n", work );
/*---------------------------------------------------------------*/
/* set current index information pointer */
/*---------------------------------------------------------------*/
pIndex[iCount] = *ppIndex;
}
/*-----------------------------------------------------------------*/
/* create an index group containing the three opened indexes */
/*-----------------------------------------------------------------*/
/*-----------------------------------------------------------------*/
/* access datastream area and initialize length */
/*-----------------------------------------------------------------*/
pDataStream = pArea; /* initialize target pointer */
ulDataLength = SIZEOF_DATA_AREA; /* initialize remaining length */
for(iCount = 0; iCount < pIndexTable->usIndexCount; iCount++ )
{
ppIndex = &pIndexTable->pIndex[iCount];/* access index info */
*pulIndexHandle = (*ppIndex)->ulHandle; /*save index handle in */
pulIndexHandle++; /*index group table */
iStatus = iStatus &
WriteDataItem (ID_XNAM, IT_ATOMIC,
VAL2(&(*ppIndex)->pName->ll) - 5,
// (USHORT )(*ppIndex)->pName->ll - 5,
(PCHAR ) (*ppIndex)->pName->value,
&ulDataLength, &pDataStream);
memset(work, 0x00, sizeof(work));
memcpy(work, (PCHAR ) (*ppIndex)->pName->value, 8 );
printf( " new index in group = %s \n", work );
printf( " index handle = %lu \n", *pulIndexHandle );
}
if (iStatus != RC_TRUE) /* check WriteDataItem status */
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
}
/*-----------------------------------------------------------------*/
/* set number of entries in index group table */
/*-----------------------------------------------------------------*/
pGroupTable->usHandleCount = iCount;
ulDataLength = (ULONG )(pDataStream - pArea);
pDataStream = pArea; /* set pointer to datastream */
/*-----------------------------------------------------------------*/
/* create an index group using API service EhwCreateIndexGroup */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwCreateIndexGroup(pSession, /* In -- session pointer */
ulDataLength, /* In -- datastream length */
pDataStream, /* In -- index listquery */
&ulGroupHandle, /* Out -- index group handle */
&ulDiagnosisInfo); /* Out -- diagnosis info */
printf ("ReturnCode (EhwCreateIndexGroup) = %d \n", ulReturnCode);
/*------------------------------------------------------------------+
| start of the search processing |
+------------------------------------------------------------------*/
ulDataLength = SIZEOF_DATA_AREA; /* initialize remaining length */
pDataStream = pArea; /* initialize target pointer */
/*-----------------------------------------------------------------*/
/* write a query datastream to the work area */
/*-----------------------------------------------------------------*/
/* write RANK option item */
iStatus = WriteDataItem (ID_RANK, IT_ATOMIC, 0, NULL,
&ulDataLength, &pDataStream);
/* write CCSID item */
/* invert the CCSID item value */
/* to big-endian format */
usValue = ID(QUERY_CCSID); /* using macro ID() or VAL2() */
iStatus = iStatus &
WriteDataItem (ID_CCSID, IT_ATOMIC,
(USHORT )sizeof(usValue), (PCHAR )&usValue,
&ulDataLength, &pDataStream);
/* write language id item */
/* invert the language id item */
/* value to big-endian format */
usValue = ID(QUERY_LANG); /* using macro ID() or VAL2() */
iStatus = iStatus &
WriteDataItem (ID_LANG, IT_ATOMIC,
(USHORT )sizeof(usValue), (PCHAR )&usValue,
&ulDataLength, &pDataStream);
/* write SARG start item */
iStatus = iStatus &
WriteDataItem (ID_SARG, IT_START, 0, NULL,
&ulDataLength, &pDataStream);
/* write TERM item */
iStatus = iStatus &
WriteDataItem (ID_TERM, IT_ATOMIC,
strlen(word1), word1,
&ulDataLength, &pDataStream);
// (USHORT )(sizeof(QUERY_WORD01) - 1),
// QUERY_WORD01,
/* write SARG end item */
iStatus = iStatus &
WriteDataItem (ID_SARG, IT_END, 0, NULL,
&ulDataLength, &pDataStream);
/* write AND item */
if( strlen(word2) > 0)
{
iStatus = iStatus &
WriteDataItem (ID_LOR, IT_ATOMIC, 0, NULL,
// WriteDataItem (ID_AND, IT_ATOMIC, 0, NULL, // to AND the terms
&ulDataLength, &pDataStream);
/* write SARG start item */
iStatus = iStatus &
WriteDataItem (ID_SARG, IT_START, 0, NULL,
&ulDataLength, &pDataStream);
/* write TERM item */
iStatus = iStatus &
WriteDataItem (ID_TERM, IT_ATOMIC,
strlen(word2), word2,
&ulDataLength, &pDataStream);
// (USHORT )(sizeof(QUERY_WORD02) - 1),
// QUERY_WORD02,
/* write SARG end item */
iStatus = iStatus &
WriteDataItem (ID_SARG, IT_END, 0, NULL,
&ulDataLength, &pDataStream);
}
if (iStatus != RC_TRUE) /* check if WriteDataItem */
{ /* status area is too small to */
/* hold the session information*/
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
}
/* set length of query data */
ulDataLength = (ULONG )(pDataStream - pArea);
pDataStream = pArea; /* set pointer to datastream */
/*-----------------------------------------------------------------*/
/* Start a search using API function EhwSearch */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwSearch (pSession, /* In -- session pointer */
ulGroupHandle, /* In -- index group handle */
ulDataLength, /* In -- datastream length */
pDataStream, /* In -- query */
&ulResultHandle, /* Out -- result handle */
&ulResultSize, /* Out -- result size */
&ulDiagnosisInfo); /* Out -- diagnosis info */
printf ("ReturnCode (EhwSearch) = %d \n", ulReturnCode);
printf ("ResultSize (EhwSearch) = %d \n", ulResultSize);
if ( ulReturnCode != RC_DONE && /* check the API return code */
ulResultSize > 0 )
{
switch (ulReturnCode) /* select the warning codes */
{
case RC_DICTIONARY_NOT_FOUND:
case RC_STOPWORD_IGNORED:
/*--------------------------------------------------------*/
/* handle the warning code ... */
/*--------------------------------------------------------*/
break; /* ignore the warning code */
case RC_INDEX_SPECIFIC_ERROR:
/*--------------------------------------------------------*/
/* get information about index-specific return codes */
/* by calling function GetProblemInfo */
/*--------------------------------------------------------*/
iStatus = GetProblemInfo (pSession, ulResultHandle,
&pIndexProblem);
if (iStatus != RC_TRUE) /* check return code */
/*-------------------------------------------------------*/
/* handle the function error ... */
/*-------------------------------------------------------*/
{
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
} /* endif GetProblemInfo failed */
/*--------------------------------------------------------*/
/* print all error return codes */
/*--------------------------------------------------------*/
if(pIndexProblem)
{
for(iCount=0;
(&pIndexProblem->IdxProblem[iCount])->IndexName;
iCount++)
{
printf("Index with Problem: %s\n",
(&pIndexProblem->IdxProblem[iCount])->IndexName);
printf("ReturnCode: %d\n",
(&pIndexProblem->IdxProblem[iCount])->usProblemRc);
}
/*--------------------------------------------------------*/
/* deallocate index problem table and related memory */
/*--------------------------------------------------------*/
for(iCount=0;
(&pIndexProblem->IdxProblem[iCount])->IndexName;
iCount++)
{
if( (&pIndexProblem->IdxProblem[iCount])->IndexName )
free((&(pIndexProblem->IdxProblem[iCount]))->IndexName);
}
free(pIndexProblem);
pIndexProblem = NULL;
} /* endif ProblemInfo returned */
break;
default:
/*--------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (RC_FALSE); /* return to the caller */
}
} /* endif API call failed */
if (ulResultSize) /* check the result size */
{
/*--------------------------------------------------------------*/
/* call API EhwCreateResultList to get a handle of the */
/* result list object */
/*--------------------------------------------------------------*/
ulReturnCode =
EhwCreateResultList(
pSession, /* In -- session pointer */
ulResultHandle, /* In -- result handle of */
/* search result */
&ulResultHandle2, /* Out -- result handle of new */
/* result list */
&ulResListSize, /* Out -- size of result list */
&ulDiagnosisInfo); /* Out -- diagnosis info */
printf ("ReturnCode (EhwCreateResultList) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (RC_FALSE); /* return to the caller */
}
/*--------------------------------------------------------------*/
/* call API function EhwRank to rank the result list */
/*--------------------------------------------------------------*/
ulReturnCode =
EhwRank( pSession, /* In -- session pointer */
ulResultHandle, /* In -- result handle of */
/* search result */
&ulDiagnosisInfo); /* Out -- diagnosis info */
printf ("ReturnCode (EhwRank) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (RC_FALSE); /* return to the caller */
}
/*--------------------------------------------------------------*/
/* build the result information for the current result list: */
/* call function ListResult */
/*--------------------------------------------------------------*/
iStatus =
ListResult (pSession, /* In -- session pointer */
ulResultHandle2, /* In -- result list handle */
ulResultSize, /* In -- result size */
LT_RESULT_DOCUMENTS, /* In -- reference limit */
pIndexTable); /* In/Out index information */
if (iStatus != RC_TRUE) /* check OpenIndex status */
{ /* index info. is not modified */
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
} /* endif ListResult failed */
/*--------------------------------------------------------------*/
/* select result information for the first index of the */
/* indexgroup using API function EhwSelectResultList: */
/* write datastream to the work area */
/*--------------------------------------------------------------*/
ulDataLength = SIZEOF_DATA_AREA; /* initialize remaining length */
pDataStream = pArea; /* initialize target pointer */
pIndexName = ((PITEM)(pIndexTable->pIndex[0]->pName))->value;
IndexNameLen = ((PITEM)(pIndexTable->pIndex[0]->pName))->ll;
/* write index name item */
iStatus = WriteDataItem (ID_XNAM, IT_ATOMIC,
(USHORT )IndexNameLen - 5,
(PCHAR ) pIndexName,
&ulDataLength, &pDataStream);
if (iStatus != RC_TRUE) /* check WriteDataItem status */
{
/*------------------------------------------------------------*/
/* handle the function error ... */
/*------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
}
ulDataLength = (ULONG )(pDataStream - pArea);
pDataStream = pArea; /* set pointer to datastream */
/*--------------------------------------------------------------*/
/* call API EhwSelectResultList */
/*--------------------------------------------------------------*/
ulReturnCode =
EhwSelectResultList(pSession, /* In -- session pointer */
ulResultHandle2, /* In -- result handle from */
/* EhwCreateResultList */
ulDataLength, /* In -- datastream length */
pDataStream, /* In -- datastream */
&ulResultHandle3, /* Out -- result list handle */
&ulResListSize, /* Out -- size of result list */
&ulDiagnosisInfo);/* Out -- diagnosis info. */
printf ("ReturnCode (EhwSelectResultList) = %d \n", ulReturnCode);
/* check the API return code */
if ( ulReturnCode != RC_DONE )
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
}
/*--------------------------------------------------------------*/
/* sort result list by rank value in descending order: */
/* write datastream to the work area */
/*--------------------------------------------------------------*/
ulDataLength = SIZEOF_DATA_AREA; /* initialize remaining length */
pDataStream = pArea; /* initialize target pointer */
/* write SSP start item */
iStatus = WriteDataItem (ID_SSP, IT_START, 0, NULL,
&ulDataLength, &pDataStream);
/* write attribute item */
attribute = SFID_RVAL;
iStatus = iStatus &
WriteDataItem (ID_SFID, IT_ATOMIC,
(USHORT )sizeof(UCHAR),
(PCHAR ) &attribute,
&ulDataLength, &pDataStream);
/* write sort order item */
iStatus = iStatus &
WriteDataItem (ID_SOD, IT_ATOMIC, 0, NULL,
&ulDataLength, &pDataStream);
/* write SSP end item */
iStatus = WriteDataItem (ID_SSP, IT_END, 0, NULL,
&ulDataLength, &pDataStream);
if (iStatus != RC_TRUE) /* check WriteDataItem status */
{
/*------------------------------------------------------------*/
/* handle the function error ... */
/*------------------------------------------------------------*/
}
ulDataLength = (ULONG )(pDataStream - pArea);
pDataStream = pArea; /* set pointer to datastream */
/*--------------------------------------------------------------*/
/* call API EhwSort */
/*--------------------------------------------------------------*/
ulReturnCode =
EhwSort (pSession, /* In -- session pointer */
ulResultHandle3, /* In -- result handle */
ulDataLength, /* In -- datastream length */
pDataStream, /* In -- datastream */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwSort) = %d \n", ulReturnCode);
/* check the API return code */
if ( ulReturnCode != RC_DONE )
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (RC_FALSE); /* return to the caller */
}
/*--------------------------------------------------------------*/
/* call function ListResult to get the sorted result list */
/*--------------------------------------------------------------*/
iStatus =
ListResult (pSession, /* In -- session pointer */
ulResultHandle3, /* In -- result handle */
ulResListSize, /* In -- size of result list */
LT_RESULT_DOCUMENTS, /* In -- reference limit */
pIndexTable); /* In/Out index information */
if (iStatus != RC_TRUE) /* check OpenIndex status */
{ /* index info. is not modified */
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
} /* endif ListResult failed */
/*--------------------------------------------------------------*/
/* delete all result lists and the search result */
/*--------------------------------------------------------------*/
iStatus =
DeleteResults (pSession, /* In -- session pointer */
ulResultHandle, /* In -- search result handle */
pIndexTable /* In -- ptr index group table*/
);
if (iStatus != RC_DONE) /* check the function status */
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
return (iStatus); /* return to the caller */
}
} /* endif result size not zero */
/*------------------------------------------------------------------+
| end of the search processing |
+------------------------------------------------------------------*/
/*-----------------------------------------------------------------*/
/* delete the index group before closing all open indexes */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwDeleteIndexGroup (pSession, /* In -- session pointer */
ulGroupHandle, /* In -- index handle */
&ulDiagnosisInfo);/* Out -- diagnosis info. */
printf ("ReturnCode (EhwDeleteIndexGroup) = %d \n", ulReturnCode);
/*-----------------------------------------------------------------*/
/* close all currently open information retrieval indexes */
/*-----------------------------------------------------------------*/
for(iCount = 0; pGroupTable->usHandleCount > 0;
pGroupTable->usHandleCount--, iCount++)
{
/* access index handle */
ulIndexHandle = pGroupTable->ulHandle[iCount];
ulReturnCode =
EhwCloseIndex (pSession, /* In -- session pointer */
ulIndexHandle, /* In -- index handle */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwCloseIndex) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
iStatus = RC_FALSE; /* set function status code */
} /* endif API call failed */
} /* endfor all open indexes */
/*-----------------------------------------------------------------*/
/* terminate search session by calling function HandleExit */
/*-----------------------------------------------------------------*/
HandleExit (pServerTable, /* In -- server table pointer */
pArea); /* In -- work area pointer */
printf ("StatusCode (IMLSMP02) = %d \n", iStatus);
return (iStatus); /* return to the caller */
} /* end of main function */
/*=====================================================================+
| |
| Entry point: ListServers |
| |
| Function: Builds a server table containing the server |
| information for any Text Search server |
| that can be connected to this application. |
| |
| Input |
| parameters: None |
| |
| Output |
| parameters: Pointer to server table |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| Calls: API functions: |
| |
| EhwListServers |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Issue an EhwListServers function call to obtain the server list |
| data stream. |
| - Check the API function return code. |
| |
| - Determine the total size of the server list: |
| Length of server list data stream plus size of server list header. |
| - Allocate the server table area in this size. |
| - Initialize the server table header fields: |
| Header text, length of table and number of server entries. |
| |
| - Parse the server list data stream: |
| While current data pointer has not yet reached the end of data |
| |
| - Select the item identifier |
| |
| - When ID_IRS (server list delimiter) |
| |
| - If it is an end item (item type = IT_END) |
| |
| - Increase the server count. |
| - Skip the current server entry. |
| |
| Else (item is of type IT_START) |
| |
| - Initialize the session pointer. |
| - Initialize the index table pointer. |
| |
| Endif |
| |
| - When ID_IRSN (server name item) |
| |
| - Set the server name length and |
| the server name of current server information structure. |
| |
| - When ID_IRSL (server location item) |
| |
| - Set the server location. |
| |
| - Otherwise - |
| |
| Endselect |
| |
| - Update the data pointer (skip current item). |
| |
| Endwhile |
| |
| - Assign the address of the server list to the output parameter. |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function ListServers (build the Server List) */
/*====================================================================*/
INT ListServers /* hold the servers in a table */
(
SRVTBL **ppServerTable /* Out -- server table pointer */
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PCHAR pDataEnd = NULL; /* end of datastream pointer */
PSERVER pServer = NULL; /* server table entry pointer */
PSRVTBL pServerTable = NULL; /* server table pointer */
ULONG ulTableLength = 0L; /* length of server table */
/*-------------------------------------------------------------------*/
/* initialize the output parameter (pointer to server table) */
/*-------------------------------------------------------------------*/
*ppServerTable = NULL;
/*-------------------------------------------------------------------*/
/* call API service EhwListServers */
/*-------------------------------------------------------------------*/
ulReturnCode =
EhwListServers (&ulDataLength, /* Out -- datastream length */
&pDataStream, /* Out -- server list */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwListServers) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*--------------------------------------------------------------*/
/* handle the API error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
/*-----------------------------------------------------------------*/
/* allocate / initialize the server list */
/*-----------------------------------------------------------------*/
/* The size of the server table can be reduced if you first parse */
/* the datastream to determine the number of servers. Then the */
/* actual size to be allocated can be calculated. */
/*-----------------------------------------------------------------*/
/* set the server table length */
ulTableLength = ulDataLength + offsetof(SRVTBL, Server[0]);
pServerTable = (PSRVTBL )malloc((size_t )ulTableLength);
if (!pServerTable) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/* write the header text */
memcpy(pServerTable->Header,
"SrvTable", sizeof(pServerTable->Header));
/* set the server table length */
pServerTable->ulTableLength = ulTableLength;
pServerTable->usServerCount = 0; /* init. the number of entries */
/* set the table entry pointer */
pServer = pServerTable->Server; /* to the first server entry */
/*-----------------------------------------------------------------*/
/* parse the server list datastream, write the table entries */
/*-----------------------------------------------------------------*/
/* set the ptr to end of data */
pDataEnd = pDataStream + ulDataLength;
/*check that eod is not reached*/
while (pDataStream < pDataEnd)
{ /* check the item identifier */
switch (((PITEM )pDataStream)->id)
{ /* invert big-endian format */
/* using macro ID() */
case ID(ID_IRS): /* server list delimiter: */
/* check if it is an end item */
if (((PITEM )pDataStream)->it == IT_END)
{
/*-----------------------------------------------------*/
/* increase number of servers, skip server table entry */
/*-----------------------------------------------------*/
pServerTable->usServerCount++;
pServer = (PSERVER )
((PCHAR )pServer + (offsetof(SERV, Name)
+ pServer->usNameLength));
}
else /* server list start item: */
{
/*-----------------------------------------------------*/
/* initialize current server information */
/*-----------------------------------------------------*/
pServer->pSession = NULL;
pServer->pIndexTable = NULL;
pServer->pGroupTable = NULL;
}
break;
case ID(ID_IRSN): /* server name item: */
/*--------------------------------------------------------*/
/* set server fields: name length and name */
/*--------------------------------------------------------*/
/* overcome big-endian format using macro VAL2() */
/*--------------------------------------------------------*/
pServer->usNameLength = VAL2(&(((PITEM )pDataStream)->ll))
- offsetof(ITEM, value[0]);
/* copy name to server table */
memcpy(pServer->Name,
((PITEM )pDataStream)->value,
(size_t )pServer->usNameLength);
break;
case ID(ID_IRSL): /* server location item: */
/*--------------------------------------------------------*/
/* hold the server location in the server table */
/*--------------------------------------------------------*/
pServer->Location = (UCHAR )*((PITEM )pDataStream)->value;
break;
default:
/* skip all unknown data items */
break;
} /* endswitch item identifier */
/* skip current data item */
/*--------------------------------------------------------------*/
/* invert big-endian format using macro VAL2() */
/*--------------------------------------------------------------*/
pDataStream += VAL2(&(((PITEM )pDataStream)->ll));
} /* endwhile not end of data */
/*-----------------------------------------------------------------*/
/* set output parameter (pointer to server table) */
/*-----------------------------------------------------------------*/
*ppServerTable = pServerTable;
return (RC_TRUE); /* return to the caller */
} /* end of ListServers */
/*=====================================================================+
| |
| Entry point: ListIndexes |
| |
| Function: Builds an index table containing |
| at most LT_NUMBER_OF_INDEXES |
| accessible information-retrieval indexes. |
| Creates and initializes the index information |
| for any index. |
| |
| Input |
| parameters: Session pointer |
| |
| Output |
| parameters: Pointer to index table |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| Calls: API functions: |
| |
| EhwListIndexes |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Determine the total size of the index table: |
| Size of index table header plus LT_NUMBER_OF_INDEXES times |
| the size of an index table pointer. |
| - Allocate the index table area. |
| - Initialize the index table header fields: |
| Header text, length of table, number of index table slots and |
| number of index entries. |
| |
| - Do until EhwListIndexes has returned the last data block |
| or there are no more slots available in the index table. |
| |
| - Issue an EhwListIndexes function call to obtain an index list |
| datastream block. |
| - If the API function indicates an error |
| - Release all storage allocated until now by this function. |
| - Return to the caller. |
| Endif |
| |
| - Parse the index list datastream block: |
| While the end of current data block is not reached |
| |
| - Check the current item identifier: |
| If it is an index name item (ID_XNAM) |
| |
| - Create and initialize the index information: |
| - Calculate the size of index information. |
| (Reserve LT_SIZEOF_LSCE_ITEM bytes for the |
| library services DLL name datastream item). |
| - Allocate the index information area. |
| If the allocation failed |
| - Release all storage allocated until now by |
| this function. |
| - Return to the caller. |
| Endif |
| - Initialize the index information header fields. |
| - Assign the current item length to structure field |
| 'length of detail datastream'. |
| - Copy the current index name item to the |
| index information area. |
| - Set the index name item pointer. |
| |
| - Update index table fields: |
| - Increase the index count in the index table. |
| - Save the current index information pointer. |
| |
| - If all slots of the index table are used |
| - Leave the while loop. |
| Endif |
| |
| Endif |
| |
| - Skip current item (update the data pointer). |
| |
| Endwhile |
| |
| Enddo |
| |
| - Assign the index table address to the output parameter. |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function ListIndexes (build an index table) */
/*====================================================================*/
INT ListIndexes /* hold the indexes in a table */
(
PVOID pSession, /* In -- session pointer */
XTBL **ppIndexTable /* Out -- index table pointer */
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PCHAR pDataEnd = NULL; /* end of datastream pointer */
PXTBL pIndexTable = NULL; /* pointer to index table */
PINDEX *ppIndex = NULL; /* ptr to index info. pointer */
USHORT usItemLength = 0; /* datastream item length */
/*-----------------------------------------------------------------*/
/* initialize the output parameter (pointer to index table) */
/*-----------------------------------------------------------------*/
*ppIndexTable = NULL;
/*-----------------------------------------------------------------*/
/* create an index table for at most LT_NUMBER_OF_INDEXES entries */
/* (LT_NUMBER_OF_INDEXES must be greater than zero !!!) */
/*-----------------------------------------------------------------*/
ulDataLength = (offsetof(XTBL, pIndex[0]) +
LT_NUMBER_OF_INDEXES * sizeof(struct IndexInfo));
pIndexTable = (PXTBL )malloc((size_t )ulDataLength);
if (!pIndexTable) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/* write the header text */
memcpy(pIndexTable->Header,
"IndexTbl", sizeof(pIndexTable->Header));
/* set the index table length */
pIndexTable->ulTableLength = ulDataLength;
/* init. the number of slots */
pIndexTable->usIndexSlots = LT_NUMBER_OF_INDEXES;
pIndexTable->usIndexCount = 0; /* init. the number of entries */
pIndexTable->usResultCount = 0; /* init. result list count */
/* set the table entry pointer */
ppIndex = pIndexTable->pIndex; /* to the first index entry */
/*-----------------------------------------------------------------*/
/* call API service EhwListIndex until end of data is indicated */
/* or the limit for number of indexes is reached */
/*-----------------------------------------------------------------*/
do
{
ulReturnCode =
EhwListIndexes (pSession, /* In -- session pointer */
&ulDataLength, /* Out -- datastream length */
&pDataStream, /* Out -- index list */
&ulDiagnosisInfo /* Out -- diagnosis info. */
);
printf ("ReturnCode (EhwListIndexes) = %d \n", ulReturnCode);
/* check the API return code */
if ((ulReturnCode != RC_DONE) &&
(ulReturnCode != RC_CONTINUATION_MODE_ENTERED))
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
free(pIndexTable); /* release the index table */
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
/*--------------------------------------------------------------*/
/* parse the index list datastream, build the table entries */
/*--------------------------------------------------------------*/
/* set the ptr to end of data */
pDataEnd = pDataStream + ulDataLength;
while (pDataStream < pDataEnd) /*check that eod is not reached*/
{ /* check the item identifier */
/* overcome big-endian format */
/* using macro ID() */
if (((PITEM )pDataStream)->id == ID(ID_XNAM))
{
/* index name item: */
/*--------------------------------------------------------*/
/* allocate storage for index information */
/*--------------------------------------------------------*/
/* overcome big-endian format using macro VAL2() */
/*--------------------------------------------------------*/
/* calculate needed data size */
usItemLength = VAL2(&(((PITEM )pDataStream)->ll));
ulDataLength = (ULONG )(offsetof(INDEX, Data[0]) +
usItemLength + LT_SIZEOF_LSCE_ITEM);
/* allocate index info struct. */
*ppIndex = (PINDEX )malloc((size_t )ulDataLength);
if (!(*ppIndex)) /* check if allocation failed */
{
/*-----------------------------------------------------*/
/* handle the allocation error ... */
/*-----------------------------------------------------*/
free(pIndexTable); /* release the index table */
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/*--------------------------------------------------------*/
/* set or initialize the index information fields */
/*--------------------------------------------------------*/
/* write the header text */
memcpy((*ppIndex)->Header,
"IndxInfo", sizeof((*ppIndex)->Header));
(*ppIndex)->ulInfoLength = ulDataLength;
(*ppIndex)->ulHandle = 0L;
(*ppIndex)->Type = 0x00;
(*ppIndex)->Property = 0x00;
(*ppIndex)->pDLL = NULL;
(*ppIndex)->ulDataLength = (ULONG )usItemLength;
(*ppIndex)->pName = (PITEM )(*ppIndex)->Data;
/* copy item to index info. */
memcpy((*ppIndex)->pName,
pDataStream, (size_t )usItemLength);
/*--------------------------------------------------------*/
/* update number of indexes and index info. pointer */
/*--------------------------------------------------------*/
pIndexTable->usIndexCount++;
ppIndex++;
/*--------------------------------------------------------*/
/* check if index table is full */
/*--------------------------------------------------------*/
if (!(pIndexTable->usIndexCount
< pIndexTable->usIndexSlots)) break;
} /* endif index name item */
/* skip current data item */
/*-----------------------------------------------------------*/
/* invert USHORT item length from 'big-endian' to 'intel' */
/* format using macro VAL2() */
/*-----------------------------------------------------------*/
pDataStream += VAL2(&(((PITEM )pDataStream)->ll));
} /* endwhile not end of data */
} while ((ulReturnCode == RC_CONTINUATION_MODE_ENTERED) &&
(pIndexTable->usIndexCount < pIndexTable->usIndexSlots));
/*-----------------------------------------------------------------*/
/* set output parameter (pointer to index table) */
/*-----------------------------------------------------------------*/
*ppIndexTable = pIndexTable;
return (RC_TRUE); /* return to the caller */
} /* end of ListIndexes */
/*=====================================================================+
| |
| Entry point: OpenIndex |
| |
| Function: Opens an informaion-retrieval index and adds the |
| index detail information to the provided |
| index information. |
| |
| Input |
| parameters: Session pointer |
| Pointer to index table |
| |
| Output |
| parameters: Pointer to index table (possibly re-allocated) |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| Calls: API functions: |
| |
| EhwOpenIndex |
| EhwGetIndexInfo |
| EhwCloseIndex (if an error occurs) |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Access the index name datastream item pointer provided with the |
| input index information. |
| |
| - Issue an EhwOpenIndex function call to open the information- |
| retrieval index. |
| - Check the API function return code. |
| - Save the returned index handle in the index information structure. |
| |
| - Issue an EhwGetIndexInfo function call to obtain the index |
| detail information datastream. |
| - If the API function return code indicates an error |
| - Invoke the API function EhwCloseIndex to close the open index. |
| - Reset the index handle field in the index information. |
| - Set the function status code. |
| - Return to the caller. |
| Endif |
| |
| - Parse the index detail information datastream: |
| While the end of data is not yet reached |
| |
| - Select the item identifier |
| |
| - When ID_XTYP (index type item) |
| |
| - Save the index type in the index information structure. |
| |
| - When ID_LSCE (library services DLL name item) |
| |
| - Check if the LSCE item fits into the index information. |
| If not then re-allocate the index information. |
| - If the re-allocation failed |
| - Invoke the API function EhwCloseIndex. |
| - Reset the current index handle. |
| - Set the function status code. |
| - Return to the caller. |
| Endif |
| - Update information length and name item pointer. |
| - Set the output parameter (index information pointer). |
| Endif |
| - Set the pointer to LSCE (library services DLL name) item. |
| - Copy the LSCE item to the index information. |
| - Update the length of index detail datastream. |
| |
| - Otherwise - |
| |
| Endselect |
| |
| - Skip current item (update the data pointer). |
| |
| Endwhile |
| |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function OpenIndex (open index, complete the index info.) */
/*====================================================================*/
INT OpenIndex /* open the specified index */
(
PVOID pSession, /* In -- session pointer */
INDEX **ppIndex /* In/Out index info. (ptr) */
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulIndexHandle = 0L; /* API index handle */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PCHAR pDataEnd = NULL; /* end of datastream pointer */
USHORT usItemLength = 0; /* datastream item length */
/* index information pointer */
PINDEX pIndex = *ppIndex;
/*-----------------------------------------------------------------*/
/* access the index name item in the index information structure */
/*-----------------------------------------------------------------*/
/* invert the item length from */
/* big-endian to intel format */
usItemLength = VAL2(&(pIndex->pName->ll));
/*-----------------------------------------------------------------*/
/* set length and pointer of index information datastream */
/*-----------------------------------------------------------------*/
ulDataLength = (ULONG )usItemLength;
pDataStream = (PCHAR )pIndex->pName;
/*-----------------------------------------------------------------*/
/* call API service to open the information retrieval index */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwOpenIndex (pSession, /* In -- session pointer */
ulDataLength, /* In -- datastream length */
pDataStream, /* In -- index list */
&ulIndexHandle, /* Out -- index handle */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwOpenIndex) = %d \n", ulReturnCode);
if (ulReturnCode == RC_INDEX_SUSPENDED)
{
/*--------------------------------------------------------------*/
/* issue a message to inform the application that the index */
/* is suspended at the moment */
/*--------------------------------------------------------------*/
return (RC_TRUE); /* return to the caller */
}
if (ulReturnCode != RC_DONE)
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
pIndex->ulHandle = ulIndexHandle; /* save the index handle */
/*-----------------------------------------------------------------*/
/* invoke API service to get the index detail information */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwGetIndexInfo (pSession, /* In -- session pointer */
ulIndexHandle, /* In -- index handle */
&ulDataLength, /* Out -- datastream length */
&pDataStream, /* Out -- index list */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwGetIndexInfo) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*--------------------------------------------------------------*/
/* handle the function error ... */
/*--------------------------------------------------------------*/
ulReturnCode = /* close current index */
EhwCloseIndex (pSession, /* In -- session pointer */
ulIndexHandle, /* In -- index handle */
&ulDiagnosisInfo);/* Out -- diagnosis info. */
printf ("ReturnCode (EhwCloseIndex) = %d \n", ulReturnCode);
pIndex->ulHandle = 0L; /* reset the index handle */
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
/*-----------------------------------------------------------------*/
/* parse the index information datastream */
/*-----------------------------------------------------------------*/
/* set the ptr to end of data */
pDataEnd = pDataStream + ulDataLength;
/* check if eod is not reached */
while (pDataStream < pDataEnd)
{ /* check the item identifier */
switch (((PITEM )pDataStream)->id)
{ /* overcome big-endian format */
/* using macro ID() */
case ID(ID_XTYP): /* index type item: */
/*--------------------------------------------------------*/
/* save index type in the index information structure */
/*--------------------------------------------------------*/
pIndex->Type = (UCHAR )*((PITEM )pDataStream)->value;
break;
case ID(ID_LSCE): /* LS client DLL item: */
/*--------------------------------------------------------*/
/* check if the DLL item fits into index information */
/*--------------------------------------------------------*/
/* invert 'big-endian' item length using macro VAL2() */
/*--------------------------------------------------------*/
usItemLength = VAL2(&(((PITEM )pDataStream)->ll));
/* determine needed info. size */
ulDataLength = (offsetof(INDEX, Data[0]) +
pIndex->ulDataLength +
(ULONG )usItemLength);
if (ulDataLength > pIndex->ulInfoLength)
{
/*-----------------------------------------------------*/
/* extend (re-allocate) the index information */
/*-----------------------------------------------------*/
pIndex = (PINDEX )realloc(pIndex, (size_t )ulDataLength);
if (!pIndex) /* check if allocation failed */
{
/*--------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------*/
ulReturnCode = /* close current index */
EhwCloseIndex
(pSession, /* In -- session pointer */
ulIndexHandle, /* In -- index handle */
&ulDiagnosisInfo); /* Out -- diagnosis info. */
printf ("ReturnCode (EhwCloseIndex) = %d \n",
ulReturnCode);
/* reset the index handle */
pIndex->ulHandle = 0L;
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/*-----------------------------------------------------*/
/* update information length and name item pointer */
/*-----------------------------------------------------*/
pIndex->ulInfoLength = ulDataLength;
pIndex->pName = (PITEM )pIndex->Data;
/*-----------------------------------------------------*/
/* set output parameter (pointer to index information) */
/*-----------------------------------------------------*/
*ppIndex = pIndex;
}
/*--------------------------------------------------------*/
/* copy LS DLL item to index information */
/*--------------------------------------------------------*/
pIndex->pDLL = (PITEM )
(pIndex->Data + pIndex->ulDataLength);
memcpy(pIndex->pDLL,
pDataStream, (size_t )usItemLength);
/* set index datastream length */
pIndex->ulDataLength += (ULONG )usItemLength;
break;
default:
break;
} /* endswitch item identifier */
/* skip current data item */
/*--------------------------------------------------------------*/
/* invert USHORT item length from 'big-endian' to 'intel' */
/* format using macro VAL2() */
/*--------------------------------------------------------------*/
pDataStream += VAL2(&(((PITEM )pDataStream)->ll));
} /* endwhile not end of data */
return (RC_TRUE);
} /* end of OpenIndex() */
/*=====================================================================+
| |
| Entry point: ListResult |
| |
| Function: Builds result information containing the search |
| result datastream and a specified number of |
| document item reference pointers. |
| (The number of references is limited by the |
| reference limit and the result size parameters.) |
| |
| Input |
| parameters: Session pointer |
| Result handle |
| Result size |
| Reference limit (maximum number of documents to be |
| referenced in the result information) |
| Index information |
| |
| Output |
| parameters: Index information |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| Calls: API functions: |
| |
| EhwGetResultList |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Determine the number of document pointers using the |
| reference limit and result size parameters and calculate |
| the size of the result information. |
| - Allocate the result information area. |
| - Initialize the result information area fields. |
| - Define a work data list structure temporarily used to |
| anchor the first result list information block. |
| |
| - Do until EhwGetResultList has returned the last data block. |
| |
| - Issue an EhwGetResultList function call to obtain a result |
| list datastream block. |
| - If the API function indicates an error |
| - If at least one data list area is allocated |
| - Save the first data list area in the result information. |
| - Set the function status code. |
| - Return to the caller. |
| Endif |
| Endif |
| |
| - Allocate a 'new' data list area for the returned data block |
| and anchor it in the 'old' data list area (next data pointer). |
| If the allocation failed |
| - Save the first data list area in the result information. |
| - Set the function status code. |
| - Return to the caller. |
| Endif |
| |
| - Initialize the data list fields (next data pointer). |
| - Save length and data block in the current data list area. |
| |
| - Update the result data length field in the result information. |
| |
| Enddo |
| |
| - Anchor the first data list area in the result information. |
| - Save the result information pointer in the index information. |
| |
| - Set the document reference pointers in the result information: |
| (Parse the result list datastream starting with the first |
| anchored data list area.) |
| While the current data list is not the last one |
| |
| While the end of current data block is not reached |
| |
| - Check the current item identifier: |
| If it is a document identifier item (ID_DID) |
| |
| - Assign the current item pointer to the current |
| document reference pointer. |
| - Increase the reference counter in the result information. |
| |
| - if the document reference limit is reached |
| - Set the function status code. |
| - Return to the caller. |
| Endif |
| |
| - Update the current document reference pointer. |
| |
| Endif |
| |
| - Skip current item (update the data pointer). |
| |
| Endwhile |
| |
| - Replace current with next data list pointer. |
| |
| Endwhile |
| |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function ListResult (build the result information) */
/*====================================================================*/
INT ListResult /* access the result list */
(
PVOID pSession, /* In -- session pointer */
ULONG ulResultHandle, /* In -- result handle */
ULONG ulResultSize, /* In -- result size */
ULONG ulReferenceLimit, /* In -- reference limit */
PXTBL pIndexTable /* In -- index table */
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PCHAR pDataEnd = NULL; /* end of datastream pointer */
PPRESULT ppResult = NULL; /* result information pointer */
PITEM *pDocument = NULL; /* ptr to document item ptr */
PITEM *pIndexItem = NULL; /* ptr to index item ptr */
PITEM *pRankValue = NULL; /* ptr to document rank value */
PITEM *pRankCount = NULL; /* ptr to document rank count */
PITEM *pWordCount = NULL; /* ptr to overall no of words */
LIST List; /* work data list structure */
PLIST pList = &List; /* current data list pointer */
PINDEX pIndex = NULL; /* pointer to Index information*/
/*-----------------------------------------------------------------*/
/* Determine number of document pointers in the result information */
/*-----------------------------------------------------------------*/
if (ulReferenceLimit > ulResultSize)
ulReferenceLimit = ulResultSize;
if (!ulReferenceLimit) /* check if the limit is zero */
ulReferenceLimit = 1L;
/* calculate result info. size */
ulDataLength = offsetof(RESULT, pDocumentInfo) +
ulReferenceLimit * sizeof(DOCINFO);
/*-----------------------------------------------------------------*/
/* Allocate and initialize the result list information: */
/* free slot where to anchor result list information is determined */
/* by variable usResultCount. */
/* Maximum number of slots is defined by LT_NUMBER_OF_RESULTS. */
/*-----------------------------------------------------------------*/
ppResult = &pIndexTable->pResult[pIndexTable->usResultCount];
*ppResult = (PRESULT )malloc((size_t )ulDataLength);
if (!*ppResult) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/* write the header text */
memcpy((*ppResult)->Header, "RsltInfo", sizeof((*ppResult)->Header));
(*ppResult)->ulInfoLength = ulDataLength;
(*ppResult)->ulHandle = ulResultHandle;
(*ppResult)->ulSize = ulReferenceLimit;
(*ppResult)->ulDataLength = 0L;
(*ppResult)->pData = NULL;
(*ppResult)->ulDocumentCount = 0L;
/*-----------------------------------------------------------------*/
/* initialize the (temporary) first data list structure */
/*-----------------------------------------------------------------*/
memset(pList, 0x00, sizeof(List));
/*-----------------------------------------------------------------*/
/* access the result list information, by calling API service */
/* EhwGetResultList (until end of data is indicated) */
/*-----------------------------------------------------------------*/
do
{
ulReturnCode =
EhwGetResultList(pSession, /* In -- session pointer */
ulResultHandle, /* In -- result handle */
&ulDataLength, /* Out -- datastream length */
&pDataStream, /* Out -- index list */
&ulDiagnosisInfo);/* Out -- diagnosis info. */
printf ("ReturnCode (EhwGetResultList) = %d \n", ulReturnCode);
/* check the API return code */
if ((ulReturnCode != RC_DONE) &&
(ulReturnCode != RC_CONTINUATION_MODE_ENTERED))
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
if (List.pNextData) /* check if a data list exists */
{ /* anchor present data lists */
(*ppResult)->pData = List.pNextData;
}
return (RC_FALSE); /* return to the caller */
} /* endif API call failed */
/*--------------------------------------------------------------*/
/* allocate a 'new' data list area, anchor it in the 'old' one */
/*--------------------------------------------------------------*/
pList->pNextData = (PLIST )
malloc((size_t )(offsetof(LIST, Data[0])
+ ulDataLength));
/*--------------------------------------------------------------*/
/* update current data list pointer */
/*--------------------------------------------------------------*/
pList = pList->pNextData; /* replace old with new ptr */
if (!pList) /* check if allocation failed */
{
/*-----------------------------------------------------------*/
/* handle the allocation error ... */
/*-----------------------------------------------------------*/
/* anchor present data lists */
(*ppResult)->pData = List.pNextData;
return (RC_FALSE); /* return to the caller */
} /* endif allocation failed */
/*--------------------------------------------------------------*/
/* save current result list block in the list data area */
/*--------------------------------------------------------------*/
pList->pNextData = NULL;
pList->ulDataLength = ulDataLength;
memcpy(pList->Data, pDataStream, (size_t )ulDataLength);
/*--------------------------------------------------------------*/
/* update total result list data length */
/*--------------------------------------------------------------*/
(*ppResult)->ulDataLength += ulDataLength;
} while (ulReturnCode == RC_CONTINUATION_MODE_ENTERED);
/*-----------------------------------------------------------------*/
/* anchor first data list area in the result information */
/*-----------------------------------------------------------------*/
(*ppResult)->pData = List.pNextData;
/*-----------------------------------------------------------------*/
/* increase number of result lists */
/*-----------------------------------------------------------------*/
pIndexTable->usResultCount++;
/*-----------------------------------------------------------------*/
/* set the document pointers (references) in the */
/* result information by parsing the chained result list data */
/*-----------------------------------------------------------------*/
if (!ulReferenceLimit) /* check the reference limit */
return (RC_TRUE);
/* start at first document ptr */
pDocument = &((*ppResult)->pDocumentInfo->pDocument);
pIndexItem = &((*ppResult)->pDocumentInfo->pIndex);
pRankValue = &((*ppResult)->pDocumentInfo->pRankValue);
pRankCount = &((*ppResult)->pDocumentInfo->pRankCount);
pWordCount = &((*ppResult)->pDocumentInfo->pWordCount);
pList = (*ppResult)->pData; /* reset current data list ptr */
while (pList) /* check if end of total */
{ /* result list data is reached */
ulDataLength = pList->ulDataLength;
pDataStream = (PCHAR )pList->Data;
/* set the ptr to end of block */
pDataEnd = pDataStream + ulDataLength;
/*--------------------------------------------------------------*/
/* parse current result list block until end of data (block) */
/* or the document reference limit is reached */
/*--------------------------------------------------------------*/
while (pDataStream < pDataEnd)
{ /* check the item identifier */
switch( ((PITEM )pDataStream)->id)
{ /* overcome big-endian format */
/* using macro ID() */
case( ID(ID_DOC) ): /* document delimiter item */
/*--------------------------------------------------------*/
/* ID_DOC delimits each document information */
/* when the document reference limit is reached stop */
/* parsing the data stream */
/*--------------------------------------------------------*/
if( ((PITEM )pDataStream)->it == IT_END )
{
if (!((*ppResult)->ulDocumentCount < ulReferenceLimit))
return (RC_TRUE); /* return to the caller */
/*-----------------------------------------------------*/
/* increase DocumentInfo structure and set pointer */
/* to structure elements */
/*-----------------------------------------------------*/
(*ppResult)->pDocumentInfo++;
pDocument = &((*ppResult)->pDocumentInfo->pDocument);
pIndexItem = &((*ppResult)->pDocumentInfo->pIndex);
pRankValue = &((*ppResult)->pDocumentInfo->pRankValue);
pRankCount = &((*ppResult)->pDocumentInfo->pRankCount);
pWordCount = &((*ppResult)->pDocumentInfo->pWordCount);
}
break;
case( ID(ID_XNAM) ): /* index identifier item: */
/*--------------------------------------------------------*/
/* save address of current index identifier item */
/*--------------------------------------------------------*/
*pIndexItem = (PITEM )pDataStream;
break;
case( ID(ID_DID) ): /* document identifier item: */
/*--------------------------------------------------------*/
/* save address of current document identifier item */
/* and address of corresponding index identifier item */
/* increase counter in the result information structure */
/*--------------------------------------------------------*/
*pDocument = (PITEM )pDataStream;
(*ppResult)->ulDocumentCount++;
break;
case( ID(ID_RVAL) ): /* rank value item: */
/*--------------------------------------------------------*/
/* save address of rank value */
/*--------------------------------------------------------*/
*pRankValue = (PITEM )pDataStream;
break;
case( ID(ID_RCNT) ): /* rank count item: */
/*--------------------------------------------------------*/
/* save address of rank count */
/*--------------------------------------------------------*/
*pRankCount = (PITEM )pDataStream;
break;
case( ID(ID_DSIZE) ): /* number of words item */
/*--------------------------------------------------------*/
/* save address of overall number of words */
/*--------------------------------------------------------*/
*pWordCount = (PITEM )pDataStream;
break;
} /* end switch datastream items */
/* skip current data item */
/*-----------------------------------------------------------*/
/* invert 'big-endian' to 'intel' format using macro VAL2() */
/*-----------------------------------------------------------*/
pDataStream += VAL2(&(((PITEM )pDataStream)->ll));
} /* endwhile not end of list */
pList = pList->pNextData; /* skip current data list */
} /* endwhile not end of result */
return (RC_TRUE);
} /* end of ListResult() */
/*=====================================================================+
| |
| Entry point: DeleteResults |
| |
| Function: Deletes the search result. |
| Result lists created by API calls EhwCreateResultList |
| EhwSelectResultList are also deleted. |
| |
| Input |
| parameters: Session pointer |
| Search result handle |
| Index Table |
| |
| Output |
| parameters: Index Table |
| |
| Return codes: Status ok RC_TRUE |
| Status not ok RC_FALSE |
| |
| Input files: None |
| |
| Output files: None |
| |
| |
| Calls: API functions: |
| |
| EhwDeleteResult |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - Issue an EhwDeleteResult function call to delete the |
| current search result and related result lists. |
| - Check the API function return code. |
| |
| - Free the result list datastreams (chained data list areas). |
| |
| - Release the chained result lists. |
| |
| |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function DeleteResults (release the result information) */
/*====================================================================*/
INT DeleteResults /* delete current result info. */
(
PVOID pSession, /* In -- session pointer */
ULONG ulResultHandle, /* In -- search result handle */
PXTBL pIndexTable /* In/Out index information */
) /* function value: status code */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulResListHandle = 0L; /* API result handle */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
INT iStatus = RC_TRUE;/* work data list structure */
PLIST pList = NULL; /* current data list pointer */
PLIST pNext = NULL; /* next data list pointer */
/* result information pointer */
/*-----------------------------------------------------------------*/
/* Call API EhwDeleteResult to delete the search result. */
/* All related result lists are also deleted. */
/*-----------------------------------------------------------------*/
ulReturnCode =
EhwDeleteResult (pSession, /* In -- session pointer */
ulResultHandle, /* In -- result handle */
&ulDiagnosisInfo/* Out -- diagnosis info */
);
printf ("ReturnCode (EhwDeleteResult) = %d \n", ulReturnCode);
if (ulReturnCode != RC_DONE) /* check the API return code */
{
/*-----------------------------------------------------------*/
/* handle the function error ... */
/*-----------------------------------------------------------*/
iStatus = RC_FALSE; /* set function status code */
} /* endif API function failed */
/*-----------------------------------------------------------------*/
/* Free the result list datastreams anchored in the result */
/* information in the index group table. */
/*-----------------------------------------------------------------*/
for(; pIndexTable->usResultCount > 0; pIndexTable->usResultCount--)
{
/* set first data list pointer */
pList = pIndexTable->pResult[pIndexTable->usResultCount-1]->pData;
while (pList) /* while not end of data lists */
{
pNext = pList->pNextData; /* save next data list pointer */
free(pList); /* release current data list */
pList = pNext; /* update pointer to data list */
} /* endwhile data list exists */
/*---------------------------------------------------------------*/
/* release current result information area */
/*---------------------------------------------------------------*/
free(pIndexTable->pResult[pIndexTable->usResultCount - 1]);
}
return (iStatus); /* return to the caller */
} /* end of DeleteResult() */
/*=====================================================================+
| |
| Entry point: GetProblemInfo |
| |
| Function: Calls API EhwGetProblemInfo to get index specific |
| error codes. |
| |
| Loops through datastream and copies index names |
| and corresponding return codes to application |
| memory. |
| |
| Input |
| parameters: - Session pointer |
| - Result Handle (returned by API EhwSearch) |
| - Address of pointer to IndexProblemTable |
| Output |
| parameters: - Updated IndexProblemTable |
| |
| Return codes: Check ok RC_TRUE |
| Check not ok RC_FALSE |
| |
| Calls: |
| |
| API function: |
| |
| EhwGetProblemInfo |
| |
| Exits: Returns to caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function GetProblemInfo */
/*====================================================================*/
INT GetProblemInfo
(
PVOID pSession, /* In -- session pointer */
ULONG ulResultHandle, /* In -- result handle */
PPBLTBL *pProblemInfo /* Out -- index problem info */
)
{
ULONG ulReturnCode = 0L; /* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
ULONG ulDataLength = 0L; /* API datastream length */
PCHAR pDataStream = NULL; /* API datastream pointer */
PCHAR pDataEnd = NULL; /* API datastream pointer */
PCHAR IndexName;
INT iCount = 0; /* loop variable */
PPBLTBL pProblem; /* Out -- index problem info */
/*-------------------------------------------------------------------*/
/* call API EhwGetProblemInfo */
/*-------------------------------------------------------------------*/
ulReturnCode = EhwGetProblemInfo (
pSession, /* In -- session pointer */
ulResultHandle, /* In -- result handle */
&ulDataLength, /* Out -- length of datastream */
&pDataStream, /* Out -- datastream */
&ulDiagnosisInfo /* Out -- diagnosis info */
); /* function value: return_code */
if( ulReturnCode ) return(RC_FALSE);
pDataEnd = pDataStream + ulDataLength;
pProblem = *pProblemInfo;
pProblem = NULL;
/*-------------------------------------------------------------------*/
/* if data was returned allocate an index problem table */
/*-------------------------------------------------------------------*/
if (ulDataLength)
{
ulDataLength = (offsetof(PBLTBL, IdxProblem[0]) +
LT_NUMBER_OF_INDEXES * sizeof(INDEXPBL));
pProblem = (PPBLTBL )malloc((size_t )ulDataLength);
if (!pProblem) /* check if allocation failed */
{
/*--------------------------------------------------------------*/
/* handle the allocation error ... */
/*--------------------------------------------------------------*/
return (RC_FALSE); /* return to the caller */
}
memcpy(pProblem->Header,
"PrblmTbl", sizeof(pProblem->Header));
/* set table length */
pProblem->ulTableLength = ulDataLength;
/* init. the number of slots */
pProblem->usTableEntries = 0;
}
/*-------------------------------------------------------------------*/
/* loop through datastream and get index name and index specific */
/* return code */
/*-------------------------------------------------------------------*/
while(pDataStream < pDataEnd)
{
switch (((PITEM )pDataStream)->id)
{ /* overcome big-endian format */
/* using macro ID() */
case ID(ID_IRX): /* index delimiter */
/* check if it is an end item */
if (((PITEM )pDataStream)->it == IT_END)
/* increase element counter */
iCount++;
break;
case ID(ID_XNAM): /* index name item */
/*--------------------------------------------------------*/
/* allocate memory and copy index name */
/*--------------------------------------------------------*/
IndexName = (&pProblem->IdxProblem[iCount])->IndexName;
ulDataLength = ((PITEM )pDataStream)->ll - 5 + 1;
IndexName = (PCHAR)malloc((size_t )ulDataLength);
if (!IndexName) /* check if allocation failed */
return (RC_FALSE); /* return to the caller */
(&pProblem->IdxProblem[iCount])->IndexName = IndexName;
memcpy(IndexName,
((PITEM )pDataStream)->value,
((PITEM )pDataStream)->ll - 5 );
break;
case ID(ID_XRC): /* index specific return code */
/*--------------------------------------------------------*/
/* copy index specific return code */
/*--------------------------------------------------------*/
(&pProblem->IdxProblem[iCount])->usProblemRc =
(USHORT)VAL2(((PITEM )pDataStream)->value);
break;
default:
/* skip all unknown data items */
break;
} /* endswitch item identifier */
/* skip current data item */
/*--------------------------------------------------------------*/
/* invert big-endian format using macro VAL2() */
/*--------------------------------------------------------------*/
pDataStream += VAL2(&(((PITEM )pDataStream)->ll));
} /* endwhile not end of data */
*pProblemInfo = pProblem;
return (RC_TRUE);
}
/*=====================================================================+
| |
| Entry point: HandleExit |
| |
| Function: Exit function of the sample main routine. |
| Releases the storage acquired by the sample |
| application program and ends pending sessions. |
| |
| Input |
| parameters: Pointer to server table |
| Pointer to work area |
| |
| Output |
| parameters: None |
| |
| Return codes: None |
| |
| Input files: None |
| |
| Output files: None |
| |
| |
| Calls: API functions: |
| |
| EhwEndSession |
| |
| Exits: Returns to caller |
| |
|----------------------------------------------------------------------|
| |
| Program logic: |
| |
| - If the server table exists |
| |
| - Do for all server information entries: |
| |
| - If there is a pending session |
| |
| - Issue an EhwEndSession function call to terminate the |
| session with the current server. |
| |
| Endif |
| |
| - If the index table exists |
| |
| - Do for all index information entries: |
| |
| - Release all anchored result information data. |
| - Free the current index information. |
| |
| Enddo |
| |
| - Release the index table. |
| |
| Endif |
| |
| Enddo |
| |
| - Release the server table. |
| |
| Endif |
| |
| - Free the work area. |
| |
| - Return to the caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function HandleExit (release allocated storage) */
/*====================================================================*/
VOID HandleExit /* clear up function for main */
(
PSRVTBL pServerTable, /* In -- server table pointer */
PCHAR pArea /* In -- work area pointer */
) /* function value: none */
{ /* function variables: */
ULONG ulReturnCode = RC_DONE;/* API return code */
ULONG ulDiagnosisInfo = 0L; /* API diagnosis information */
PVOID pSession = NULL; /* API session pointer */
PXTBL pIndexTable = NULL; /* index table pointer */
PSERVER pServer = NULL; /* server information pointer */
PINDEX pIndex = NULL; /* index information pointer */
PRESULT pResult = NULL; /* result information pointer */
PLIST pList = NULL; /* data list pointer */
PLIST pNext = NULL; /* data list pointer */
INT iCount = 0; /* loop variable */
/*-----------------------------------------------------------------*/
/* release storage allocated outside a session */
/*-----------------------------------------------------------------*/
if (pServerTable) /* check the server table ptr */
{
pServer = pServerTable->Server; /* initialize server info. ptr */
while (pServerTable->usServerCount)
{
/*-----------------------------------------------------------*/
/* free session related storage allocated by API functions */
/*-----------------------------------------------------------*/
pSession = pServer->pSession; /* set first session pointer */
if (pSession) /* check if session is started */
{ /* end the API session */
ulReturnCode =
EhwEndSession (pSession, /* In -- session pointer */
/* Out -- diagnosis info */
&ulDiagnosisInfo);
printf ("ReturnCode (EhwEndSession) = %d \n",
ulReturnCode);
}
/*-----------------------------------------------------------*/
/* free session related storage acquired by sample functions */
/*-----------------------------------------------------------*/
/* check if index group exists */
if (pServer->pGroupTable)
free (pServer->pGroupTable); /* free index group table */
pIndexTable = pServer->pIndexTable;
if (pIndexTable) /* check if index table exists */
{
for(; iCount < pIndexTable->usResultCount; iCount++)
{
pResult = pIndexTable->pResult[iCount];
if (pResult) /* check result info. pointer */
{ /* set first data list pointer */
pList = pResult->pData;
while (pList) /* while not end of data lists */
{ /* save next data list pointer */
pNext = pList->pNextData;
free(pList); /* release current data list */
pList = pNext; /* update pointer to data list */
} /* endwhile data list exists */
free(pResult); /* free result information */
}
}
for(iCount=0; iCount<pIndexTable->usIndexCount; iCount++)
/* release current index info. */
free(pIndexTable->pIndex[iCount]);
free(pIndexTable); /* release the index table */
}
/* update server info. pointer */
pServer = (PSERVER )
((PCHAR )pServer + (offsetof(SERV, Name)
+ pServer->usNameLength));
(pServerTable->usServerCount)--;
}
free(pServerTable); /* release the server table */
}
if (pArea) free(pArea); /* release the work area */
return; /* return to the caller */
} /* end of HandleError() */
/*=====================================================================+
| |
| Entry point: WriteDataStream |
| |
| Function: Writes a specified datastream item to the provided |
| area. |
| |
| It is checked, if the item fits into the remaining |
| buffer space (if yes, the length of the remaining |
| space and corresponding pointer are updated). |
| |
| Conversion of USHORT variables between 'intel' and |
| 'big-endian' formats is done within this function |
| for two-byte identifiers and lengths using VAL2 |
| macro. The item values are written as provided. |
| Input |
| parameters: - Item identifier |
| - Item type |
| - Length of item value (may be zero) |
| - Item value (optional) |
| - Length of remaining space |
| - Pointer to remaining space |
| Output |
| parameters: - Updated length of remaining space (for RC_TRUE) |
| - Updated pointer to remaining space (for RC_TRUE) |
| |
| Return codes: Check ok RC_TRUE |
| Check not ok RC_FALSE |
| |
| Exits: Returns to caller. |
| |
+=====================================================================*/
/*====================================================================*/
/* internal function WriteDataItem (write datastream item) */
/*====================================================================*/
INT WriteDataItem
(
USHORT usItemId, /* In -- item identifier */
UCHAR ItemType, /* In -- item type */
USHORT usValueLength, /* In -- length of item value */
PCHAR pValue, /* In -- ptr to item value */
PULONG pulAreaLength, /* In/Out remaining area size */
PPCHAR ppArea /* In/Out ptr to target area */
)
{
USHORT usItemLL; /* total length of data item */
PITEM pItem; /* pointer to data stream item */
pItem = (PITEM )*ppArea; /* set pointer to target area */
/* calculate total item length */
usItemLL = offsetof(ITEM, value[0]) + usValueLength;
/* check remaining area length */
if ((ULONG )usItemLL > *pulAreaLength) return (RC_FALSE);
/* write item ll/id/it to area */
pItem->ll = VAL2(&usItemLL); /* invertion to big-endian */
pItem->id = VAL2(&usItemId); /* format using macro VAL2() */
pItem->it = ItemType;
/* if provided, write */
if (usValueLength) /* item value to target area */
memcpy(pItem->value, pValue, (size_t )usValueLength);
*ppArea += usItemLL; /* update current area pointer */
*pulAreaLength -= usItemLL; /* update remaining area len. */
return (RC_TRUE);
} /* end of WriteDataItem() */
/*====================================================================*/