// Change History
// 03/18/04 AV Development: Add DRS_VectorVirtualPeriodCount, DRS_VectorVirtualPeriodDescr
// 12/10/03 AV Development: Add ProcessCount, DRS_ProcessClearCache, DRS_ProcessCachedNames funcs
// 11/19/03 AV Development: Remove development version of the DRS_FieldMaxSize func
// 11/19/03 AV Development: Merge Production version 9
// 11/05/03 AV Production: Add  DRS_FieldMaxSize( DRS_Field const *pField, uint * Size)
// 10/23/03 AV Development: Add macro def services

#ifndef _H_AT_CIF_H_
#define _H_AT_CIF_H_

#include <windows.h>

#include "base/AT_GlobalTypes.h"
#include <vector>
#include <utility>         

#include "base/at_defs.h"

#include "drs_type.h"

	// Calling conventions
#ifdef WIN16
  #define _drs_call_h _pascal
  #define _drs_call_c _pascal _export FAR
#else //Win32
  #define _drs_call_h __declspec(dllexport) _stdcall
  #define _drs_call_c _stdcall
#endif


extern "C" // Prevent C++ name mangling
{

//Initialization/Termination
DLL_Erc _drs_call_h DRS_Initialize( char *sApplID, char *sIniFile);
DLL_Erc _drs_call_h DRS_Terminate();
DLL_Handle _drs_call_h DRS_ApplicationGet();
DLL_Handle _drs_call_h DRS_ApplicationSelect(DLL_Handle app);

//Search fields
DLL_Erc _drs_call_h DRS_SearchFieldCount( uint16 *iCount);
DLL_Erc _drs_call_h DRS_SearchFieldDescr( uint16 iSearchField, DRS_Descriptor *pDescr);
DLL_Erc _drs_call_h DRS_SearchFieldHide( uint16 iSearchField, bool * IsHide);
DLL_Erc _drs_call_h DRS_SearchFieldIndexCount( uint16 iSearchField, uint16 *pIndexCount);
DLL_Erc _drs_call_h DRS_SearchFieldIndexOpen( uint16 iSearchField, uint16 iIndex, DLL_HandlePtr ppIndex);
DLL_Erc _drs_call_h DRS_SearchFieldIndexIsSortable( uint16 iSearchField, uint16 iIdx, bool *pIsSortable);
DLL_Erc _drs_call_h DRS_SearchFieldDataFieldCount( uint16 iSearchFieldIdx, uint16 *pCount);
//DLL_Erc _drs_call_h DRS_SearchFieldDataFieldID( uint16 iSearchFieldIdx, uint16 iDataFieldIdx, uint *pFieldID);
DLL_Erc _drs_call_h DRS_SearchFieldDataField( uint16 iSearchFieldIdx, uint16 iDataFieldIdx, DLL_HandlePtr pDataField);
DLL_Erc _drs_call_h DRS_SearchFieldFieldMapID( uint16 iSearchField, int16 *pFieldMapID);

//Data fields
DLL_Erc _drs_call_h DRS_FieldCount( uint16 *pCount);
DLL_Erc _drs_call_h DRS_FieldGet( uint16 iField, DLL_HandlePtr pField);
DLL_Erc _drs_call_h DRS_FieldApplID( DLL_Handle pField, uint * pApplID);
DLL_Erc _drs_call_h DRS_FieldApportionGroup( DLL_Handle pField, byte * sDest);
DLL_Erc _drs_call_h DRS_FieldDescr( DLL_Handle pField, DRS_Descriptor *pElem);
DLL_Erc _drs_call_h DRS_FieldMaxSize( DLL_Handle pField, uint * Size);
DLL_Erc _drs_call_h DRS_FieldStateCount( DLL_Handle pField, uint16 *pCount);
DLL_Erc _drs_call_h DRS_FieldHide( DLL_Handle pField, bool * IsHide);
DLL_Erc _drs_call_h DRS_FieldStateDescr( DLL_Handle pField, uint16 iState, DRS_Descriptor *pElem);
DLL_Erc _drs_call_h DRS_FieldOccurrences( DLL_Handle pRecord, DLL_Handle pField, uint16 *pFieldOccurences);
DLL_Erc _drs_call_h DRS_FieldDataLen( DLL_Handle pRecord, DLL_Handle pField, uint16 iState, uint16 iOccurrence, uint16 *pFieldLen);
DLL_Erc _drs_call_h DRS_FieldDataGet( DLL_Handle pRecord, DLL_Handle pField, uint16 iState, uint16 iOccurrence, byte *sDest, uint16 iDestLen);

//FieldMaps
DLL_Erc _drs_call_h DRS_FieldMapCount(uint16 *pCount);
DLL_Erc _drs_call_h DRS_FieldMapGet(uint16 iFieldMap, DLL_HandlePtr pFieldMap);
DLL_Erc _drs_call_h DRS_FieldMapEntryCount(DLL_Handle pFieldMap, uint16 *pEntryCount);
DLL_Erc _drs_call_h DRS_FieldMapStateCount(DLL_Handle pFieldMap, uint16 *pStateCount);
DLL_Erc _drs_call_h DRS_FieldMapStateDescr(DLL_Handle pFieldMap, uint16 iState, DRS_Descriptor *pDescr);
DLL_Erc _drs_call_h DRS_FieldMapEntryGet(DLL_Handle pFieldMap, uint16 iState, uint16 iEntry, byte *sEntry, uint16 iLen);
DLL_Erc _drs_call_h DRS_FieldMapStateEntryToMapEntry(DLL_Handle pFieldMap, uint16 iState, uint16 iEntry, uint16 *pMapEntry);

//Vectors
DLL_Erc _drs_call_h DRS_VectorCount( uint16 *pCount);
DLL_Erc _drs_call_h DRS_VectorDescr( uint16 iVectorID, DRS_Descriptor *pDescr);
DLL_Erc _drs_call_h DRS_VectorDepth( uint16 iVectorID, uint16 *pDepth);
DLL_Erc _drs_call_h DRS_VectorDimDescr( uint16 iVectorID, uint16 iDim, DRS_Descriptor *curElem);
DLL_Erc _drs_call_h DRS_VectorDimIsCollective( uint16 iVector, uint16 iDim, bool *pIsCollective);
DLL_Erc _drs_call_h DRS_VectorDimIsConstant( uint16 iVector, uint16 iDim, bool *pIsConstant);
DLL_Erc _drs_call_h DRS_VectorDimMaxLength( uint16 iVectorID, uint16 iDim, uint * pMaxLength);

//Vector nodes retrieved by address.
DLL_Erc _drs_call_h DRS_VectorNodeCount( uint16 iVectorID, uint16 iDim, VectorAddress VectorAddress[], uint *pCount);
DLL_Erc _drs_call_h DRS_VectorNodeDescr( uint16 iVectorID, uint16 iDim, VectorAddress VectorAddress[], DRS_Descriptor *curElem);

//Vector nodes retrieved by record occurrence.
//Some applications may wish to display only nodes which actually contain data in a particular record.
//User retrieves new DRS_OccurrenceCollection object.
//OccurrenceCollection object is filled in by DRS_VectorNodeOccurrences().
//Use OccurrenceCollection functions to retrieve occurrence info.
//(Underlying data structure is vector<pair<uint ID, uint ordinal_number>>. Ordinal number unused.

#define DRS_OccurrenceCollection std::vector<uint>

DLL_Erc _drs_call_h DRS_VectorNodeOccurrencesGet( DLL_Handle pRecord,
                                                  uint16 iVector,
                                                  VectorAddress addr[],
                                                  uint16 iDepth,
                                                  uint16 isUnique,
                                                  DLL_HandlePtr ppOccs);

DLL_Erc _drs_call_h DRS_VectorNodeOccurrenceCount(DLL_Handle pOccs,
                                              uint *iCount);

DLL_Erc _drs_call_h DRS_VectorNodeOccurrenceAddress(DLL_Handle pOccs,
                                                uint iOcc,
                                                VectorAddress *pAddress);

DLL_Erc _drs_call_h DRS_VectorNodeOccurrencesClose(DLL_Handle pOccs);

//DLL_Erc _drs_call_h DRS_OccurrenceCollectionNew( std::vector< pair<uint,uint>> ** ppvOccurrences);
//DLL_Erc _drs_call_h DRS_OccurrenceCollectionCount( DRS_OccurrenceCollection const *pvOccurrences, uint iCount);
//DLL_Erc _drs_call_h DRS_OccurrenceCollectionGetID( DRS_OccurrenceCollection const *pvOccurrences, uint iID);

//DLL_Erc _drs_call_h DRS_VectorNodeOccurrences( uint16 iVectorID, uint16 iDim, uint32 VectorAddress[], DRS_RecordSet *pRecord, DRS_OccurrenceCollection *pvOccurrences);

//Vector periods
DLL_Erc _drs_call_h DRS_VectorPeriodCount( uint16 iVectorID, bool isIndex, uint16 *pCount);
DLL_Erc _drs_call_h DRS_VectorVirtualPeriodCount( uint16 iVectorID, bool isIndex, uint16 *pCount);
DLL_Erc _drs_call_h DRS_VectorPeriodDescr( uint16 iVectorID, uint16 iPeriod, bool isIndex, DRS_Descriptor *pDescriptor);
DLL_Erc _drs_call_h DRS_VectorVirtualPeriodDescr( uint16 iVectorID, uint16 iPeriod, bool isIndex, DRS_Descriptor *pDescriptor);
DLL_Erc _drs_call_h DRS_VectorIndexPeriodToDataPeriod( uint16 iVectorID, uint16 iIndexPeriod, uint16 *pDataPeriod);

//Vector states
DLL_Erc _drs_call_h DRS_VectorStateCount( uint16 iVectorID, uint16 *pCount);
DLL_Erc _drs_call_h DRS_VectorStateDescr( uint16 iVectorID, uint16 iState, DRS_Descriptor *pDescriptor);

//Vector formulas
DLL_Erc _drs_call_h DRS_VectorFormulaCount( uint16 iVectorID, uint16 *pCount);
DLL_Erc _drs_call_h DRS_VectorFormulaDescr( uint16 iVectorID, uint16 iFormula, DRS_Descriptor * pDescriptor);
DLL_Erc _drs_call_h DRS_VectorFormulaInfo( uint16 iVectorID, uint16 iFormula, DRS_Formula_Info * pFormulaInfo);
DLL_Erc _drs_call_h DRS_VectorFormulaIsReport( uint16 iVectorID, uint16 iFormula, bool *pIsReport);
DLL_Erc _drs_call_h DRS_VectorFormulaIsMutable( uint16 iVectorID, uint16 iFormula, bool *pIsMutable);
DLL_Erc _drs_call_h DRS_VectorFormulaIsSumable( uint16 iVectorID, uint16 iFormula, bool *pIsSumable);
DLL_Erc _drs_call_h DRS_VectorFormulaIsGroupable( uint16 iVectorID, uint16 iFormula, bool *pIsGroupable);

//Vector indexes
DLL_Erc _drs_call_h DRS_VectorIndexOpen( uint16 iVectorID, VectorAddress Address[],
                                         uint16 iIndexState, uint16 iPeriod, DLL_HandlePtr ppIndex);
DLL_Erc _drs_call_h DRS_Index_HasCounts( DLL_Handle pIndex, bool *pHasCounts);
DLL_Erc _drs_call_h DRS_Index_IsSeek( DLL_Handle pIndex, bool *pIsSeek);  //Seek only on TEXT and INTEGER_FIXED_WIDTH indexes
                                                                             //Seek on INTEGER is meaningless.
DLL_Erc _drs_call_h DRS_Index_IsText( DLL_Handle pIndex, bool *pIsText);  //Return index type
DLL_Erc _drs_call_h DRS_Index_Search( DLL_Handle pIndex, unsigned char *sSearchVal, DLL_HandlePtr ppRecList);
DLL_Erc _drs_call_h DRS_Index_TermCount( DLL_Handle pIndex, uint32 *lCount);
DLL_Erc _drs_call_h DRS_Index_TermGet( DLL_Handle pIndex, uint32 lIdx, byte *sDest, uint16 iDestLen);
DLL_Erc _drs_call_h DRS_Index_Seek( DLL_Handle pIndex, byte *sSeekString, uint32 *pRetIdx);
DLL_Erc _drs_call_h DRS_Index_Close( DLL_Handle pIndex);

//Vector data
//Get vector data by address; Returns Vector data and isAvail.
DLL_Erc _drs_call_h DRS_VectorDataGet( DLL_Handle pRecord, uint16 iVector, VectorAddress Address[], uint16 iFormula, DLL_Handle ppResults, bool *pIsAvail);

DLL_Erc _drs_call_h DRS_VectorMaxPrecision( uint16 iVectorID, uint *pMaxPrecision);

//Results
DLL_Erc _drs_call_h DRS_ResultSetOpen( uint16 iVectorID, DLL_HandlePtr ppFormulaResults);
DLL_Erc _drs_call_h DRS_ResultSetClose( uint16 iVectorID, DLL_Handle ppFormulaResults);
DLL_Erc _drs_call_h DRS_ResultRealGet( DLL_Handle ppFormulaResults, uint16 iItem, uint iPrecision, double *pRealResult);
DLL_Erc _drs_call_h DRS_ResultIntGet( DLL_Handle ppFormulaResults, uint16 iItem, int32 *pIntResult);

//Index Iterators
DLL_Erc _drs_call_h DRS_IndexIter_New( DLL_Handle pIndex, DLL_HandlePtr ppIter);
DLL_Erc _drs_call_h DRS_IndexIter_Close( DLL_Handle pIter);
DLL_Erc _drs_call_h DRS_IndexIter_Next( DLL_Handle pIter);
DLL_Erc _drs_call_h DRS_IndexIter_Prev( DLL_Handle pIter);
DLL_Erc _drs_call_h DRS_IndexIter_Seek( DLL_Handle pIter, long lOffset);
DLL_Erc _drs_call_h DRS_IndexIter_SeekTerm( DLL_Handle pIndex, DLL_Handle pIter, byte *sSeekString, uint32 *pRetIdx);
DLL_Erc _drs_call_h DRS_IndexIter_TermGet( DLL_Handle  pIndex, DLL_Handle pIter, byte *sDest, uint16 iDestLen, uint32 *pOccurrences);

//Record lists
DLL_Erc _drs_call_h DRS_RecList_New( DLL_HandlePtr ppRecList);
DLL_Erc _drs_call_h DRS_RecList_Copy( DLL_Handle pRecListSrc, DLL_HandlePtr ppRecListDest);
DLL_Erc _drs_call_h DRS_RecList_Connect( DLL_Handle pRecListDest, DLL_Handle pRecListSource, uint16 connector);
DLL_Erc _drs_call_h DRS_RecList_Invert( DLL_Handle pRecListDest);
DLL_Erc _drs_call_h DRS_RecList_Count( DLL_Handle pRecList, uint32 *cnt);
DLL_Erc _drs_call_h DRS_RecList_Close( DLL_Handle pRecList);
DLL_Erc _drs_call_h DRS_RecList_Add ( DLL_Handle pRecListSrc , uint32 idx, DLL_Handle pRecListDest);
DLL_Erc _drs_call_h DRS_RecList_Remove (DLL_Handle pRecListSrc, uint32 idx, DLL_Handle pRecListDest);
DLL_Erc _drs_call_h DRS_RecList_IsOneOf (DLL_Handle pRecListSrc, uint32 * pidx, DLL_Handle pRecListDest, bool *pIsOne);
DLL_Erc _drs_call_h DRS_RecList_AbsRecGet (DLL_Handle pRecListSrc, uint32 idx, uint32 *pAbsRecNo);
DLL_Erc _drs_call_h DRS_RecList_Sort( DLL_Handle pRecListSrc, sortRec cif_ctxts[], uint16 iCount, HWND hParent, bool *pIsCancel);
DLL_Erc _drs_call_h DRS_RecList_TermCount( DLL_Handle pRecListSrc, DLL_Handle index, bool *pIsCancel, uint * iCount);

//Record list iterators
DLL_Erc _drs_call_h DRS_RecListIter_New( DLL_Handle pRecList, DLL_HandlePtr ppRLIter);
DLL_Erc _drs_call_h DRS_RecListIter_Close( DLL_Handle pRLIter);
DLL_Erc _drs_call_h DRS_RecListIter_Next( DLL_Handle pRLIter);
DLL_Erc _drs_call_h DRS_RecListIter_Prev( DLL_Handle pRLIter);
DLL_Erc _drs_call_h DRS_RecListIter_Seek( DLL_Handle pRLIter, long lOffset);

//Records
DLL_Erc _drs_call_h DRS_RecordGet( DLL_Handle p_iter, DLL_HandlePtr ppRecord);
DLL_Erc _drs_call_h DRS_RecordClose( DLL_Handle pRecord);

//Reports
DLL_Erc _drs_call_h DRS_ReportNew( DRS_Descriptor *pDescriptor, DLL_HandlePtr ppReport);
DLL_Erc _drs_call_h DRS_ReportClose( DLL_Handle pReport);
DLL_Erc _drs_call_h DRS_ReportAddVector( DLL_Handle pReport, uint16 iVectorID, VectorAddress VectorSelector[]);
DLL_Erc _drs_call_h DRS_ReportAddSubreport( DLL_Handle pReport, uint16 iSearchFieldID);
DLL_Erc _drs_call_h DRS_ReportGenerate( DLL_Handle pReport, DLL_Handle pRecordList, bool *pIsCancel);

//Report tree retrieval
DLL_Erc _drs_call_h DRS_ReportTreeGetRoot( DLL_Handle pReportTree, DLL_HandlePtr ppNode);
DLL_Erc _drs_call_h DRS_ReportTreeDepth( DLL_Handle pReportTree, uint16 *pDepth);
DLL_Erc _drs_call_h DRS_ReportTreeDimDescr( DLL_Handle pReportTree, uint16 iDim, DRS_Descriptor *pDescriptor);
DLL_Erc _drs_call_h DRS_ReportTreeNodeGet( DLL_Handle pReportTree, VectorAddress ReportAddress[], uint16 iDim, DLL_HandlePtr ppNode);

//A Report tree's vector trees
//Each report node will return these vector trees.
DLL_Erc _drs_call_h DRS_ReportTreeVectorTreeCount( DLL_Handle pReportTree, uint32 *pCount);
DLL_Erc _drs_call_h DRS_ReportTreeVectorTreeSelector( DLL_Handle pReportTree, uint iVectorTree, VectorAddress *addrSelector);
DLL_Erc _drs_call_h DRS_ReportVectorTree2ApplVectorTree( DLL_Handle pReportTree, uint iReportVectorTree, VectorAddress *pApplVectorID);

//Report Nodes
DLL_Erc _drs_call_h DRS_ReportNodeQualifierLen( DLL_Handle pReportNode, uint16 *pLen);
DLL_Erc _drs_call_h DRS_ReportNodeQualifierGet( DLL_Handle pReportNode, byte *sDest, uint16 iDestLen);
DLL_Erc _drs_call_h DRS_ReportNodeChildCount( DLL_Handle pReportNode, uint32 *pChildCount);
DLL_Erc _drs_call_h DRS_ReportNodeChildGet( DLL_Handle pReportNode, uint32 lChild, DLL_HandlePtr ppNode);
//Get the root of a report's vector tree.
DLL_Erc _drs_call_h DRS_ReportNodeVectorTreeGet( DLL_Handle pReportNode, uint16 iVectorIdx, DLL_HandlePtr ppVectorNode); //Gets root node

//A vector tree's nodes
//A report's vector tree returns a node and its ID in the APPLICATIONS's vector tree.
DLL_Erc _drs_call_h DRS_ReportVectorNodeChildCount( DLL_Handle pVectorNode, uint *pCount);
DLL_Erc _drs_call_h DRS_ReportVectorNodeChildGet( DLL_Handle pVectorNode, uint iApplVector, uint16 iDepth, uint iChildIdx, uint *pChildID, DLL_HandlePtr ppChildNode);
DLL_Erc _drs_call_h DRS_ReportVectorNodeChildGetByID( DLL_Handle pVectorNode, uint iChildID, DLL_HandlePtr ppChildNode);

//Node MUST be leaf, else Exception
DLL_Erc _drs_call_h DRS_ReportVectorNodeDataGet( DLL_Handle pReportVectorNode, DLL_Handle ppResults);

//Exceptions
DLL_Erc _drs_call_h DRS_ExceptionPop( byte *sDest, uint16 iDestLen);
DLL_Erc _drs_call_h DRS_ExceptionGet( uint i, byte *sDest, uint16 iDestLen);
uint16  _drs_call_h DRS_ExceptionCount();
int16   _drs_call_h DRS_ExceptionPopLen(); // Last exception. Returns -1 if no exceptions
int16   _drs_call_h DRS_ExceptionGetLen(uint i); // Returns -1 if no exceptions

} // Extern "C"
#endif
