/* SCCSID("@(#)gsstest.h   %E%   SAP   %I%") */

/************************************************************************/
/* $Id: //tools/src/freeware/gsstest/gsstest.h#4 $
 ************************************************************************
 *
 * Copyright (c) 1998-2000  SAP AG.  All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer. 
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. All advertising materials mentioning features or use of this
 *    software must display the following acknowledgment:
 *    "This product includes software developed by SAP AG"
 *
 * 4. The name "SAP AG" must not be used to endorse or promote products
 *    derived from this software without prior written permission.
 *    For written permission, please contact www.press@sap.com
 *
 * 5. Redistributions of any form whatsoever must retain the following
 *    acknowledgment:
 *    "This product includes software developed by SAP AG"
 *
 * THIS SOFTWARE IS PROVIDED BY SAP AG ``AS IS'' AND ANY EXPRESSED
 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED. SAP AG SHALL BE LIABLE FOR ANY DAMAGES
 * ARISING OUT OF THE USE OF THIS SOFTWARE ONLY IF CAUSED BY SAP AG'S
 * INTENT OR GROSS NEGLIGENCE. IN CASE SAP AG IS LIABLE UNDER THIS
 * AGREEMENT FOR DAMAGES CAUSED BY SAP AG'S GROSS NEGLIGENCE SAP AG
 * FURTHER SHALL NOT BE LIABLE FOR ANY INDIRECT, INCIDENTAL, SPECIAL,
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
 * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 * OR TORT, AND SHALL NOT BE LIABLE IN EXCESS OF THE AMOUNT OF
 * DAMAGES TYPICALLY FORESEEABLE FOR SAP AG, WHICH SHALL IN NO EVENT
 * EXCEED US$ 500.000.- 
 *
 ************************************************************************/


#ifndef _GSSTEST_H_
#  define _GSSTEST_H_

#define PROG_EXE_NAME	"gsstest"

#define OPTIONS_FILE	"gtopts"
#define PARENT_CTX_FILE	"gtctxpar"
#define CHILD_CTX_FILE  "gtctxcld"


#ifdef _WIN32
#  define WIN32_LEAN_AND_MEAN 1
#  include <windows.h>
#  define sleep(x)   Sleep( (x)*1000 )
#  define putenv(x)  _putenv(x)
#endif

#include "common.h"


#define CFREE( ptr ) if ( (ptr)!=NULL ) { free(ptr);  ptr = NULL; }

typedef enum gss_call_e {
   GSS_INIT_SEC_CONTEXT1 = 0,
   GSS_INIT_SEC_CONTEXT2,
   GSS_INIT_SEC_CONTEXT3,
   GSS_INIT_SEC_CONTEXT4,
   GSS_ACCEPT_SEC_CONTEXT1,
   GSS_ACCEPT_SEC_CONTEXT2,
   GSS_ACCEPT_SEC_CONTEXT3,
   GSS_ACCEPT_SEC_CONTEXT4,
   GSS_EXPORT_SEC_CONTEXT_I,
   GSS_EXPORT_SEC_CONTEXT_A,
   GSS_IMPORT_SEC_CONTEXT_I,
   GSS_IMPORT_SEC_CONTEXT_A,
   GSS_INQUIRE_CONTEXT,
   GSS_CONTEXT_TIME,
   GSS_DELETE_SEC_CONTEXT,
   GSS_PROCESS_CONTEXT_TOKEN,

   GSS_GET_MIC,
   GSS_VERIFY_MIC,
   GSS_WRAP,
   GSS_UNWRAP,
   GSS_WRAP_SIZE_LIMIT,

   GSS_ACQUIRE_CRED_I,
   GSS_ACQUIRE_CRED_A,
   GSS_ADD_CRED,
   GSS_INQUIRE_CRED_I,
   GSS_INQUIRE_CRED_A,
   GSS_INQUIRE_CRED_BY_MECH,
   GSS_RELEASE_CRED,

   GSS_IMPORT_NAME,
   GSS_CANONICALIZE_NAME,
   GSS_COMPARE_NAME,
   GSS_DISPLAY_NAME,
   GSS_DUPLICATE_NAME,
   GSS_EXPORT_NAME,
   GSS_RELEASE_NAME,

   GSS_DISPLAY_STATUS,
   GSS_INDICATE_MECHS,
   GSS_INQUIRE_MECHS_FOR_NAME,
   GSS_INQUIRE_NAMES_FOR_MECH,
   GSS_RELEASE_BUFFER,

   GSS_ADD_OID_SET_MEMBER,
   GSS_CREATE_EMPTY_OID_SET,
   GSS_TEST_OID_SET_MEMBER,
   GSS_RELEASE_OID_SET,
   GSS_INVALID_CALL
} gss_call_et;

#define GSS_CALL_ENUM_MAX  (GSS_INVALID_CALL)


#include "gssapi_2.h"
#include "gss_argm.h"
#include "sncgss.h"
#include "load_dll.h"
#include "debug.h"
#include "verbose.h"

#define SNC_LIMITS_31_AND_4X	1

#define BIG_MESSAGE_SIZE	32000

/* SAP specific constraints on GSS-API characteristics/behaviour/performance	       */
#ifdef SNC_LIMITS_31_AND_4X

#  define SNC_LIMITS_LABEL   "R/3 Releases 3.1x, 4.0x, 4.5x"
   /* Current Limits for SNC (SAP R/3 3.1x and 4.0x, 4.5x) */

#  define SNC_NAME_MAXLEN	          90u  /* max. length printable name	          (bytes)    */
#  define SNC_ACLKEY_MAXLEN              126u  /* max. length binary canonical name       (bytes)    */
#  define SNC_MAX_MIC_TOKEN              128u  /* max. length MIC token		          (bytes)    */
#  define SNC_MAX_WRAP_INCREASE          128u  /* max. length wrap() message growth       (bytes)    */
#  define SNC_MAX_CONTEXT_TOKEN        25000u  /* max. length context establishment token (bytes)    */
#  define SNC_MAX_EXPORTED_CTX_TOKEN    8000u  /* max. exported context token length      (bytes)    */
#  define SNC_MAX_ESTABLISHMENT_TIME 1000000   /* max. context establishment time         (microsec) */
#  define SNC_MAX_GUI_ESTAB_TIME     8000000   /* max. context establishment time for Gui (microsec) */
#  define SNC_MAX_CTX_XFER_TIME         3000   /* max. context xfer time                  (microsec) */
#  define SNC_GOOD_CTX_XFER_TIME        1500   /* recom. max context xfer time            (microsec) */
#  define SNC_MIN_INTEG_SPEED	         500   /* min. integrity protection speed         (Bytes/s)  */
#  define SNC_GOOD_INTEG_SPEED          2000   /* recom. min integrity protection speed   (Bytes/s)  */
#  define SNC_MIN_CONF_SPEED             200   /* min. confidentiality protection speed   (Bytes/s)  */
#  define SNC_GOOD_CONF_SPEED           1000   /* recom. min confidentiality prot speed   (Bytes/s)  */
#  define SNC_MAX_GSS_CONTEXT_TIME      1000   /* max. time for gss_context_time()        (microsec) */
#  define SNC_MAX_MIC_LATENCY           9000   /* max. getmic()/verifymic() latency	  (microsec) */
#  define SNC_MAX_WMIC_LATENCY          9500   /* max. wrap(mic)/unwrap(mic) latency	  (microsec) */
#  define SNC_MAX_WCONF_LATENCY	       10000   /* max. wrap(conf)/unwrap(conf) latency	  (microsec) */
#  define SNC_MAX_CRCTX_LIFETIME_DIFF  (5*60u) /* max. lifetime difference cred<context   (seconds)  */
#  define SNC_REQUIRED_FLAGS   (GSS_C_TRANS_FLAG)

#else

   /* Future/planned limits for SNC interoperability */
#  define SNC_NAME_MAXLEN	         240u  /* max. length printable name	          (bytes)    */
#  define SNC_ACLKEY_MAXLEN              500u  /* max. length binary canonical name       (bytes)    */
#  define SNC_MAX_MIC_TOKEN             1500u  /* max. length MIC token		          (bytes)    */
#  define SNC_MAX_WRAP_INCREASE         1500u  /* max. length wrap() message growth       (bytes)    */
#  define SNC_MAX_CONTEXT_TOKEN        25000u  /* max. length context establishment token (bytes)    */
#  define SNC_MAX_EXPORTED_CTX_TOKEN    8000u  /* max. exported context token length      (bytes)    */
#  define SNC_MAX_ESTABLISHMENT_TIME 1000000   /* max. context establishment time         (microsec) */
#  define SNC_MAX_GUI_ESTAB_TIME     8000000   /* max. context establishment time for Gui (microsec) */
#  define SNC_MAX_CTX_XFER_TIME         3000   /* max. context xfer time                  (microsec) */
#  define SNC_GOOD_CTX_XFER_TIME        1500   /* recom. max context xfer time            (microsec) */
#  define SNC_MIN_INTEG_SPEED	        1000   /* min. integrity protection speed         (Bytes/s)  */
#  define SNC_GOOD_INTEG_SPEED          2000   /* recom. min integrity protection speed   (Bytes/s)  */
#  define SNC_MIN_CONF_SPEED             500   /* min. confidentiality protection speed   (Bytes/s)  */
#  define SNC_GOOD_CONF_SPEED           1000   /* recom. min confidentiality prot speed   (Bytes/s)  */
#  define SNC_MAX_GSS_CONTEXT_TIME      1000   /* max. time for gss_context_time()        (microsec) */
#  define SNC_MAX_MIC_LATENCY           3000   /* max. getmic()/verifymic() latency	  (microsec) */
#  define SNC_MAX_WMIC_LATENCY          3200   /* max. wrap(mic)/unwrap(mic) latency	  (microsec) */
#  define SNC_MAX_WCONF_LATENCY	        4000   /* max. wrap(conf)/unwrap(conf) latency	  (microsec) */
#  define SNC_MAX_CRCTX_LIFETIME_DIFF  (5*60u) /* max. lifetime difference cred<context   (seconds)  */
#  define SNC_REQUIRED_FLAGS   (GSS_C_TRANS_FLAG)

#endif


/* which message sizes are considered by    */
/* the message protection speed calculation */
#define MINSIZE_FOR_STATISTICS	  400u
#define MAXSIZE_FOR_STATISTICS	20000u

/* Maximum tolerated lifetime skew between the context   */
/* lifetime of the initiator and the context lifetime    */
/* of the acceptor -- there may be a difference due to   */
/* slow authentication (smartcards, LDAP-requests, etc). */
#define MAX_CTX_LIFETIME_SKEW      20

#define KNOWN_GSS_CONTEXT_FLAGS	 \
   (   GSS_C_DELEG_FLAG		 \
     | GSS_C_MUTUAL_FLAG	 \
     | GSS_C_REPLAY_FLAG	 \
     | GSS_C_SEQUENCE_FLAG	 \
     | GSS_C_CONF_FLAG		 \
     | GSS_C_INTEG_FLAG		 \
     | GSS_C_ANON_FLAG		 \
     | GSS_C_PROT_READY_FLAG	 \
     | GSS_C_TRANS_FLAG )

#define SYMMETRIC_GSS_CONTEXT_FLAGS \
   (   GSS_C_DELEG_FLAG		 \
     | GSS_C_MUTUAL_FLAG	 \
     | GSS_C_REPLAY_FLAG	 \
     | GSS_C_SEQUENCE_FLAG	 \
     | GSS_C_CONF_FLAG		 \
     | GSS_C_INTEG_FLAG		 \
     | GSS_C_ANON_FLAG		 \
     | GSS_C_TRANS_FLAG	)

#define SYMMETRIC_GSS_CONTEXT_FLAGS_2_LIBS \
   (   GSS_C_DELEG_FLAG		 \
     | GSS_C_MUTUAL_FLAG	 \
     | GSS_C_CONF_FLAG		 \
     | GSS_C_INTEG_FLAG		 \
     | GSS_C_ANON_FLAG )

#define SNC_CONTEXT_FLAGS	 \
   (   GSS_C_MUTUAL_FLAG	 \
     | GSS_C_REPLAY_FLAG	 \
     | GSS_C_INTEG_FLAG		 \
     | GSS_C_CONF_FLAG		 \
     | GSS_C_TRANS_FLAG	)

#define BOGUS_VALUE    1234567890l
#define BOGUS_POINTER  ((void *) &bogus_ptr[3])

#define BOGUS_OID      ((gss_OID)       BOGUS_POINTER)
#define BOGUS_OID_SET  ((gss_OID_set)   BOGUS_POINTER)
#define BOGUS_NAME     ((gss_name_t)    BOGUS_POINTER)
#define BOGUS_CRED     ((gss_cred_id_t) BOGUS_POINTER)
#define BOGUS_CONTEXT  ((gss_ctx_id_t)  BOGUS_POINTER)

#define BOGUS_INI_MINOR(parm) \
   (parm) = (options.bogus_check==0) ? 0 : BOGUS_VALUE;

#define BOGUS_INI_OID(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? GSS_C_NO_OID : BOGUS_OID; }
#define BOGUS_INI_OID_SET(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? GSS_C_NO_OID_SET : BOGUS_OID_SET; }
#define BOGUS_INI_NAME(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? GSS_C_NO_NAME : BOGUS_NAME; }
#define BOGUS_INI_CRED(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? GSS_C_NO_CREDENTIAL : BOGUS_CRED; }
#define BOGUS_INI_CONTEXT(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? GSS_C_NO_CONTEXT : BOGUS_CONTEXT; }
#define BOGUS_INI_VALUE(parm) \
   if ( (parm)!=NULL ) { *(parm) = (options.bogus_check==0) ? 0 : BOGUS_VALUE; }
#define BOGUS_INI_BUFFER(parm) \
   if ( (parm)!=NULL ) { (parm)->value  = (options.bogus_check==0) ? 0 : BOGUS_POINTER;	\
			 (parm)->length = (options.bogus_check==0) ? 0 : BOGUS_VALUE;   }

#define BOGUS_CHECK_OID(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_OID ) {			  \
      rc++;				     			  \
      XVEB((V_ERR, "%s returned BOGUS gss_OID %s!\n",		  \
	    gss_call, (parm_name) ));				  \
      *(parm) = GSS_C_NO_OID;					  \
   }

#define BOGUS_CHECK_OID_SET(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_OID_SET ) {			  \
      rc++;				     			  \
      XVEB((V_ERR, "%s returned BOGUS gss_OID_set %s!\n",	  \
	    gss_call, (parm_name) ));				  \
      *(parm) = GSS_C_NO_OID_SET;	 				  \
   }

#define BOGUS_CHECK_NAME(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_NAME ) {			  \
      rc++;				     			  \
      XVEB((V_ERR, "%s returned BOGUS gss_name_t %s!\n",	  \
	    gss_call, (parm_name) ));				  \
      *(parm) = GSS_C_NO_NAME;		     			  \
   }

#define BOGUS_CHECK_CRED(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_CRED ) {			  \
      rc++;				     			  \
      XVEB((V_ERR, "%s returned BOGUS credential handle %s!\n",	  \
	    gss_call, (parm_name) ));				  \
      *(parm) = GSS_C_NO_CREDENTIAL;				  \
   }

#define BOGUS_CHECK_CONTEXT(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_CONTEXT ) {		  \
      rc++;				     			  \
      XVEB((V_ERR, "%s returned BOGUS context handle %s!\n",	  \
	    gss_call, (parm_name) ));				  \
      *(parm) = GSS_C_NO_CONTEXT;		  		  \
   }

#define BOGUS_CHECK_VALUE(parm, parm_name)			  \
   if ( (parm)!=NULL && *(parm)==BOGUS_VALUE ) {		  \
      if ( maj_stat==GSS_S_COMPLETE ) {				  \
	 rc++;				     			  \
	 XVEB((V_ERR, "%s returned BOGUS value %s!\n",	          \
		      gss_call, (parm_name) ));			  \
      }								  \
      *(parm) = 0;		  			          \
   }

#define BOGUS_CHECK_BUFFER(parm, parm_name)			  \
   if ( (parm)!=NULL ) {					  \
      int  v = ((parm)->value  == BOGUS_POINTER);		  \
      int  l = ((parm)->length == BOGUS_VALUE);			  \
								  \
      if ( v || l ) {						  \
         rc++;							  \
         XVEB((V_ERR, "%s returned BOGUS buffer-(%s%s%s) %s!\n",  \
	    gss_call,						  \
	    (v!=0) ? "value"     : "",				  \
	    (v!=0 && l!=0) ? "+" : "",				  \
	    (l!=0) ? "length"	 : "",				  \
	    parm_name ));					  \
	 (parm)->value  = NULL;					  \
	 (parm)->length = 0;					  \
      }								  \
   }


typedef enum snc_qop_e {
   SNC_QOP_OPEN	     = 1,
   SNC_QOP_INTEGRITY = 2,
   SNC_QOP_PRIVACY   = 3
} snc_qop_et;

typedef enum sc_variants_e {
      SNC_SIMPLE_CRED = 1,
      SNC_CHECKED_CRED,
      SNC_GSSNAMED_CRED,
      SNC_PRNAMED_CRED,
      SNC_PRNAMED_VIA_XP_CRED,
      SNC_MISNAMED_CRED
} sc_variants_et;


typedef enum oid_type_e {
   OID_ANY      = 0,
   OID_NAMETYPE,
   OID_MECHANISM
} oid_type_et;


typedef enum tmsg_type_e {
   TMSG_TYPE_MICONLY,
   TMSG_TYPE_WMIC,
   TMSG_TYPE_WCONF
} tmsg_type_et;


struct tmsg_entry {
   struct tmsg_entry  * next;
   gss_buffer_desc      ori_msg;
   DLL_GSSFP_T	      * gssfp_token;
   gss_buffer_desc      gss_token;
   DLL_GSSFP_T	      * gssfp_message;
   gss_buffer_desc      gss_ret_msg;
   gss_qop_t		qop;
   tmsg_type_et         msg_type;
   int                  conf_flag;
};


/* public enum and structure definition of Jobs for test_message_exchange()   */

#define TMA_CTXTIME	   (1<< 6)
#define TMA_ACC		   (1<< 7)
#define TMA_INI		   (1<< 8)
#define TMA_END		   (1<< 9)
#define TMA_ADDMSG	   (1<<10)
#define TMA_PROCMSG	   (1<<11)
#define TMA_EXPLORE	   (1<<12)


 
typedef enum tmsg_action_e {
   TMSG_END_OF_LIST     = 0,
   TMSG_ACT_END_QUIT	= TMA_END ,      /* end of Job, release queue buffers unprocessed       */
   TMSG_ACT_END_STOP	= TMA_END+1,     /* end of Job, return with no further queue processing */

   TMSG_ACT_A_MICONLY	= (TMA_INI|TMA_ADDMSG|TMA_CTXTIME),    /* A creates a mic token for B       (opt. length)	*/
   TMSG_ACT_A_WMIC	= (TMA_INI|TMA_ADDMSG|TMA_CTXTIME)+1,  /* A creates a wrap token for B      (opt. length)	*/
   TMSG_ACT_A_WCONF	= (TMA_INI|TMA_ADDMSG|TMA_CTXTIME)+2,  /* A creates a conf wrap token for B (opt. length)	*/

   TMSG_ACT_B_MICONLY	= (TMA_ACC|TMA_ADDMSG|TMA_CTXTIME),    /* B creates a mic token for A       (opt. length)	*/
   TMSG_ACT_B_WMIC	= (TMA_ACC|TMA_ADDMSG|TMA_CTXTIME)+1,  /* B creates a wrap token for B      (opt. length)	*/
   TMSG_ACT_B_WCONF	= (TMA_ACC|TMA_ADDMSG|TMA_CTXTIME)+2,  /* B creates a conf wrap token for A (opt. length)	*/

   TMSG_ACT_A_TAKE_MSG  = (TMA_INI|TMA_PROCMSG|TMA_CTXTIME),	     /* A processes one message from queue_A		*/
   TMSG_ACT_B_TAKE_MSG  = (TMA_ACC|TMA_PROCMSG|TMA_CTXTIME),	     /* B processes all queued messages from queue_B	*/
   TMSG_ACT_AB_TAKE_MSG = (TMA_INI|TMA_ACC|TMA_PROCMSG|TMA_CTXTIME), /* process A and B queues round robin		*/

   TMSG_REFLECT_ON_A	= TMA_EXPLORE,    /* reflection attack on A	*/
   TMSG_REFLECT_ON_B	= TMA_EXPLORE+ 1, /* reflection attack on B	*/
   TMSG_ACT_A_DELMSG    = TMA_EXPLORE+ 2, /* delete a message for A	*/
   TMSG_ACT_B_DELMSG    = TMA_EXPLORE+ 3, /* delete a message for B	*/
   TMSG_ACT_A_DUPMSG    = TMA_EXPLORE+ 4, /* duplicate a message for A	*/
   TMSG_ACT_B_DUPMSG    = TMA_EXPLORE+ 5, /* duplicate a message for B	*/
   TMSG_ACT_A_REORDER   = TMA_EXPLORE+ 6, /* reorder messages for A	*/
   TMSG_ACT_B_REORDER   = TMA_EXPLORE+ 7, /* reorder messages for B	*/

   TMSG_ACT_A_CTXTRANS  = (TMA_INI|TMA_EXPLORE|TMA_CTXTIME) + 8, /* context transfer of context A */
   TMSG_ACT_B_CTXTRANS  = (TMA_ACC|TMA_EXPLORE|TMA_CTXTIME) + 8, /* context transfer of context B */
   TMSG_ACT_LOC_FTRANS	= TMA_EXPLORE+ 9, /* context transfer of context A */
   TMSG_ACT_CHILD_FTRANS= TMA_EXPLORE+10, /* context transfer of context A */

   TMSG_ACT_MSG_TIMING  = TMA_EXPLORE+11, /* print timing data for msg prot     */
   TMSG_ACT_XFER_TIMING = TMA_EXPLORE+12, /* print timing data for context xfer */
   TMSG_ACT_CLEAR_TIMING= TMA_EXPLORE+13, /* clear msg and xfer timing data     */

   TMSG_ACT_CTX_REFRESH	= TMA_EXPLORE+14, /* try to refresh a security context  */

   TMSG_ACT_INVALID

} tmsg_action_et;



typedef enum mp_test_e {

   MP_TEST_REFLECT	=  1,
   MP_TEST_REPLAY	=  2,
   MP_TEST_REORDER	=  3,
   MP_TEST_DELMSG	=  4,
   MP_TEST_NORMAL	=  5,
   MP_TEST_TRUNC	=  6,
   MP_TEST_TRUNC_2	=  7,
   MP_TEST_TRUNC_3	=  8,
   MP_TEST_TRAIL_GARB	=  9,
   MP_TEST_MOD_MIDDLE	= 10,
   MP_TEST_MOD_TAIL	= 11,
   MP_TEST_SIMUL_FRAME	= 12,

   MP_TEST_MASK		= (1<<10)-1,
   MP_TEST_INI		= (1<<10),
   MP_TEST_ACC		= (1<<11),
   MP_TEST_MICONLY	= (1<<12),
   MP_TEST_WMIC		= (1<<13),
   MP_TEST_WCONF	= (1<<14)

} mp_test_et;


#define BENCH_WCONF   0
#define BENCH_WMIC    1
#define BENCH_MICONLY 2

struct tmsg_job {
   tmsg_action_et	action;
   union {
      size_t		size;
      void	      * ptr;
      char	      * label;
   } u;
};


typedef enum ctx_type_e {
   CTX_INITIATOR = 0,
   CTX_ACCEPTOR  = 1
} ctx_type_et;

struct ctx_desc {
   DLL_GSSFP_T	  * gssfp;	    /* static copy		  */
   char		  * label;	    /* Strmaxdup()ed		  */
   OM_uint32	    flags_req;	    /* requested context flags    */
   OM_uint32	    lifetime_req;   /* requested context lifetime */
   gss_name_t	    ini_name;	    /* dynamic			  */
   gss_buffer_desc  ini_prname;	    /* VERBOSE_DUPMEM		  */
   gss_name_t	    acc_name;	    /* dynamic			  */
   gss_buffer_desc  acc_prname;	    /* VERBOSE_DUPMEM		  */
   gss_name_t	    src_name;	    /* dynamic (acc/inquire)	  */
   gss_name_t	    targ_name;	    /* dynamic			  */
   gss_ctx_id_t	    ctx;	    /* dynamic			  */
   gss_cred_id_t    cred;	    /* dynamic			  */
   sc_variants_et   cred_type;	    /* requested sap_cred type    */
   gss_qop_t	    qop;	    /* requested QOP for msgprot  */
   OM_uint32	    flags;	    /* received context flags	  */
   OM_uint32	    lifetime;	    /* received context lifetime  */
   OM_uint32	    cred_lifetime;  /* credential lifetime        */
   time_t	    enter;	    /* time of context establishment */
   ctx_type_et	    type;           /* type of context (initiator/acceptor) */
};


struct range_list {
   size_t  stop;
   size_t  start;
};

struct defined_ranges_s {
   struct range_list * ranges;
   char              * rlabel;
};


/* Function prototypes and global data exports from various sources */


/********************************/
/*  gsstest.c   -- Export list  */
/********************************/

extern    char  * gsstest_version;
extern    Ulong	  timedelay;   /* delay of individual API-calls (microsec)         */
extern    char    bogus_ptr[];
extern	  int	  missing_msg_prot;
extern    char  * prog_exe_name;
extern    int     ignore_name_for_statistics;
extern    int     testing_kerberos;

extern	 gss_OID_desc nt_ini_oid[1];
extern   gss_OID_desc nt_acc_oid[1];

#define bool_opt  Uint

struct prog_options_s {
   bool_opt    bogus_check;
   bool_opt    sap_constraints;
   bool_opt    try_msgprot_anyway;
   bool_opt    cross_process_xfer;
   bool_opt    force_xfer;
   bool_opt    child_process;
   bool_opt    zap_trailing_nuls;
   bool_opt    test_errors;
   bool_opt    error_location;
   bool_opt    log_tee;
   bool_opt    try_user_errors;
   Uint	       verbose_level;
   Uint        show_timing_data;
   Uint        num_parallel_contexts;
   Uint	       wrap_range_level;
   Uint        mech_to_use;
   char      * dll_name_1;
   char	     * dll_name_2;
   char      * target;
   char      * initiator;
   char      * logfile;
};

extern struct prog_options_s options;

void  clean_options( void );

FILE  * open_logfile( char * filename, char * mode, int with_tee );
void    tail_logfile( FILE * logfp );


int   parent_main(	   DLL_GSSFP_T	  * p_gssfp_ini,
			   DLL_GSSFP_T	  * p_gssfp_acc	    );

int   child_main(	   DLL_GSSFP_T	  * p_gssfp_ini,
			   DLL_GSSFP_T	  * p_gssfp_acc	    );	 

int   set_static_nt_oid(   DLL_GSSFP_T	  * p_gssfp,
			   gss_OID	    p_target_oid,
			   gss_OID	    p_oid	    );

void  print_gssapi_statistics(
			   DLL_GSSFP_T	  * p_gssfp_ini,
			   DLL_GSSFP_T	  * p_gssfp_acc,
			   int		    p_rc	    );

void  show_command_line(   int		    argc,
			   char	         ** argv	    );


int   print_sncadapter_info( DLL_GSSFP_T  * p_gssfp,
			     char         * p_prefix	    );

int   find_builtin_snc_adapter(
			     gss_OID_set    p_mech_set	    );

void  verify_snc_builtin_info(
			   DLL_GSSFP_T    * p_gssfp,
			   char		  * p_prefix	    );

void  show_snc_limits(	   char		  * p_prefix	    );

/********************************/
/*  contexts.c  -- Export list  */
/********************************/

int   context_tests(	   DLL_GSSFP_T	     * p_gssfp_ini,
			   DLL_GSSFP_T	     * p_gssfp_acc  );


int   delete_sec_context(  int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   gss_ctx_id_t	     * pp_ctx,
			   gss_buffer_t	       p_fin_token,
			   OM_uint32	     * pp_maj_stat  );


int   context_time(	   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   gss_ctx_id_t	       p_ctx,
			   OM_uint32	     * pp_lifetime,
			   OM_uint32	     * pp_maj_stat  );


int   init_sec_context(	   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   int		     * pp_num_call,
			   gss_cred_id_t       p_cred,
			   gss_ctx_id_t	     * pp_ctx,
			   gss_name_t          p_target_name,
			   gss_OID	       p_mech,
			   OM_uint32	       p_in_flags,
			   OM_uint32	       p_in_lifetime,
			   gss_channel_bindings_t  p_chbind,
			   gss_buffer_t	       p_in_token,
			   gss_OID	     * pp_actual_mech,
			   gss_buffer_t	       p_out_token,
			   OM_uint32	     * pp_out_flags,
			   OM_uint32	     * pp_out_lifetime,
			   OM_uint32	     * pp_maj_stat  );


int   accept_sec_context(  int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   int		     * pp_num_call,
			   gss_ctx_id_t	     * pp_ctx,
			   gss_cred_id_t       p_cred,
			   gss_buffer_t	       p_in_token,
			   gss_channel_bindings_t  p_chbind,
			   gss_name_t	     * pp_src_name,
			   gss_OID	     * pp_mech_type,
			   gss_buffer_t	       p_out_token,
			   OM_uint32	     * pp_out_flags,
			   OM_uint32	     * pp_lifetime,
			   gss_cred_id_t     * pp_deleg_cred,
			   OM_uint32	     * pp_maj_stat  );


int   export_sec_context(  int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   ctx_type_et	       p_usagetype,
			   gss_ctx_id_t	     * pp_ctx,
			   gss_buffer_t	       p_export_token,
			   OM_uint32	     * pp_maj_stat  );


int   import_sec_context(  int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   ctx_type_et	       p_usagetype,
			   gss_buffer_t	       p_export_token,
			   gss_ctx_id_t	     * pp_ctx,
			   OM_uint32	     * pp_maj_stat  );


int   inquire_context(	   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   gss_ctx_id_t	       p_ctx,
			   gss_name_t	     * pp_src_name,
			   gss_name_t	     * pp_targ_name,
			   OM_uint32	     * pp_lifetime,
			   gss_OID	     * pp_mech_type,
			   OM_uint32	     * pp_ctx_flags,
			   int		     * pp_local_ini,
			   int		     * pp_open,
			   OM_uint32	     * pp_maj_stat  );


int   print_ctx_flags(	   int		       p_trclevel,
			   char		     * p_gss_call,
			   char		     * p_parm_name,
			   OM_uint32	     * pp_flags	    );


int   establish_context(   int		       p_trclevel,
			   OM_uint32	       p_flags_req,
			   OM_uint32	       p_lifetime_req,
			   gss_OID	       p_ini_mech,
			   struct ctx_desc   * p_ini,
			   struct ctx_desc   * p_acc,
			   gss_OID	     * pp_ini_mech,
			   gss_OID	     * pp_acc_mech,
			   OM_uint32	     * pp_maj_stat  );


int   sap_establish_context(
			   int		       p_trclevel,
			   OM_uint32	       p_flags,
			   OM_uint32	       p_lifetime,
			   DLL_GSSFP_T	     * p_gssfp_ini,
			   DLL_GSSFP_T	     * p_gssfp_acc,
			   struct ctx_desc  ** pp_ini,
			   struct ctx_desc  ** pp_acc,
			   sc_variants_et      p_ini_cred_type,
			   sc_variants_et      p_acc_cred_type,
			   void		     * p_target,
			   size_t	       p_target_len,
			   OM_uint32	     * pp_maj_stat  );


int   sap_try_context(	   int		       p_trclevel,
			   OM_uint32	       p_flags,
			   OM_uint32	       p_lifetime,
			   DLL_GSSFP_T	     * p_gssfp_ini,
			   DLL_GSSFP_T	     * p_gssfp_acc,
			   sc_variants_et      p_ini_cred_type,
			   sc_variants_et      p_acc_cred_type,
			   char		     * p_target,
			   size_t	       p_target_len,
			   size_t	       p_count	    );


int   ctx_transfer_cycle(  int		       p_trclevel,
			   struct ctx_desc   * p_ctx	    );


int   refresh_context(	   int		       p_trclevel,
			   OM_uint32	       p_lifetime,
			   struct ctx_desc  ** pp_ini,
			   struct ctx_desc  ** pp_acc,
			   int		     * pp_success    );

struct ctx_desc  *
      create_ctx_desc(	   DLL_GSSFP_T	     * p_gssfp,
			   char		     * p_label,
			   void		     * p_initiator,
			   size_t	       p_initiator_len,
			   gss_OID	       p_ini_nt,
			   void		     * p_acceptor,
			   size_t	       p_acceptor_len,
			   gss_OID	       p_acc_nt	    );

int   release_ctx_desc(	   struct ctx_desc  ** pp_ctx	    );


/********************************/
/*  names.c     -- Export list  */
/********************************/

int   name_tests(	   DLL_GSSFP_T	  * gssfp	    );

int   release_name(	   DLL_GSSFP_T    * gssfp,
			   gss_name_t	  * name	    );

int   print_name(	   int		    trc_level,
			   DLL_GSSFP_T	  * gssfp,
			   char		  * type_of_name,
			   gss_name_t	    name,
			   int		  * pp_wsp_count,
			   gss_OID	  * pp_oid,
			   OM_uint32	  * pp_maj_stat	    );

int   display_name(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_name_t	    p_name,
			   gss_buffer_t	    p_buffer,
			   gss_OID	  * pp_oid,
			   OM_uint32	  * pp_maj_stat	    );

int   import_name(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   char		  * p_name,
			   size_t	    p_name_len,
			   gss_OID	    p_nt_oid,
			   gss_name_t	  * pp_gssname,
			   OM_uint32	  * pp_maj_stat	    );

int   export_name(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_name_t	    p_name,
			   gss_buffer_t	    p_expname,
			   OM_uint32	  * pp_maj_stat	    );

int   compare_names(	   int		    p_trclevel,
			   DLL_GSSFP_T    * p_gssfp,
			   gss_name_t	    p_name1,
			   gss_name_t	    p_name2,
			   int		  * pp_result,
			   OM_uint32	  * pp_maj_stat	    );

int   canonicalize_name(   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_name_t	    p_name,
			   gss_OID	    p_mech_oid,
			   gss_name_t	  * pp_cname,
			   OM_uint32	  * pp_maj_stat	    );

int   import_and_canonicalize(
			   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   void		  * p_prname,
			   size_t	    p_prname_len,
			   gss_OID	    p_nametype,
			   gss_name_t	  * pp_out_name,
			   OM_uint32	  * pp_maj_stat	    );

int   verify_same_name(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   char		  * p_prefix,
			   char		  * p_label1,
			   gss_name_t	    p_name1,
			   char		  * p_label2,
			   gss_name_t	    p_name2	    );

int   name_to_aclkey(	   int		    p_trclevel,
			   DLL_GSSFP_T    * p_gssfp,
			   gss_name_t	    p_name_in,
			   int		    p_canon_first,
			   int              p_use_export_name,
			   void		 ** pp_xpname,
			   size_t         * pp_xpname_len,
			   gss_OID	  * pp_nametype,
			   OM_uint32	  * pp_maj_stat	    );

int   verify_same_aclkey(  int		    p_trclevel,
			   char		  * p_prefix,
			   char		  * p_label1,
			   int		    p_do_can1,
			   DLL_GSSFP_T	  * p_gssfp1,
			   gss_name_t	    p_name1,
			   char		  * p_label2,
			   int		    p_do_can2,
			   DLL_GSSFP_T	  * p_gssfp2,
			   gss_name_t	    p_name2	    );

int   name_transform_xp(   int		    p_trclevel,
			   DLL_GSSFP_T    * p_gssfp,
			   gss_name_t	    p_in_name,
			   gss_name_t	  * pp_out_name,
			   OM_uint32	  * pp_maj_stat	    );

int   name_transformations( int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_name_t	    p_in_name,
			   void		  * p_in_buffer,
			   size_t	    p_in_buffer_len,
			   gss_OID	    p_in_nametype,
			   OM_uint32	  * pp_maj_stat	    );


int   dump_exported_name(  int		    p_trclevel,
			   DLL_GSSFP_T    * p_gssfp,
			   char		  * p_name_label,
			   gss_name_t	    p_name,
			   OM_uint32	  * pp_maj_stat	    );

int   decode_asn1_length(  unsigned char  * p_buf,
			   size_t	    p_buf_len,
			   size_t         * pp_enc_len,
			   size_t	  * pp_len_value    );

int   dump_exported_name_framing(
			   void		  * p_buf,
			   size_t	    p_buf_len	    );



/********************************/
/*  oids.c	-- Export list  */
/********************************/
extern gss_OID	     nt_anonymous;
extern gss_OID	     nt_export_name;
extern gss_OID	     nt_user_name;
extern gss_OID	     nt_machine_uid;
extern gss_OID	     nt_string_uid;
extern gss_OID	     nt_hb_service;
extern gss_OID	     nt_hb_service_alt;

char   * oid_to_str(	   gss_OID	    p_oid	    );

int	 compare_oid(	   gss_OID	    p_oid1,
			   gss_OID	    p_oid2	    );

int	 validate_oid(	   DLL_GSSFP_T	  * p_gssfp,
			   oid_type_et	    p_oid_type,
			   char		  * p_prefix,
			   char		  * p_name_oid,
			   gss_OID	    p_oid	    );

int	 validate_oidset(  DLL_GSSFP_T	  * p_gssfp,
			   oid_type_et	    p_oid_type,
			   char		  * p_prefix,
			   char		  * p_name_set,
			   gss_OID_set	    p_oid_set	    );

int	 compare_oid_set(  gss_OID_set	    p_oid_set1,
			   gss_OID_set	    p_oid_set2	    );

int	 check_oid_in_oidset(
			   int		    vlevel,
			   char		  * p_name,
			   gss_OID	    p_oid,
			   char		  * p_name_set,
			   gss_OID_set	    p_oid_set	    );

int	 check_oid_subset( int		    vlevel,
			   char		  * p_name_set1,
			   gss_OID_set	    p_oid_set1,
			   char		  * p_name_set2,
			   gss_OID_set	    p_oid_set2	    );

int	 verify_oid_subset( int		    p_trclevel,
			   char		  * p_prefix,
			   char		  * p_name_set1,
			   gss_OID_set	    p_oid_set1,
			   char		  * p_name_set2,
			   gss_OID_set	    p_oid_set2	    );

int	 print_oid(	   int		    vlevel,
			   char		  * p_name,
		  	   gss_OID	    p_oid	    );

void	 dump_oid_cstruct( int		    p_trclevel,
			   char		  * p_prefix,
			   gss_OID	    p_oid	    );

int	 print_oid_set(	   int		    vlevel,
			   char		  * p_name,
			   gss_OID_set	    p_oid_set	    );

int      release_oid_set(  DLL_GSSFP_T    * gssfp,
			   gss_OID_set    * oid_set	    );

int      oid_in_oid_set(   gss_OID_set      p_oid_set,
			   gss_OID          p_oid           );

 
/********************************/
/*  creds.c	-- Export list  */
/********************************/

int   cred_tests(	   DLL_GSSFP_T	  * p_gssfp_ini,
			   DLL_GSSFP_T	  * p_gssfp_acc	    );

int   release_cred(	   DLL_GSSFP_T	  * p_gssfp,
			   gss_cred_id_t  * cred	    );

int   acquire_cred(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_cred_usage_t p_usage,
			   gss_name_t	    p_name,
			   gss_OID_set	    p_desired_mechs,
			   gss_cred_id_t  * pp_cred,
			   gss_OID_set	  * pp_actual_mechs,
			   OM_uint32	  * pp_lifetime,
			   OM_uint32	  * pp_maj_stat	    );

int   inquire_cred(	   int		    p_trclevel,
			   DLL_GSSFP_T	  * p_gssfp,
			   gss_cred_id_t    p_cred,
			   ctx_type_et	    p_usagetype,
			   gss_name_t	  * pp_name,
			   OM_uint32	  * pp_lifetime,
			   gss_cred_usage_t * pp_usage,
			   gss_OID_set    * pp_mechanisms,
			   OM_uint32	  * pp_maj_stat	    );


int   check_cred(	   DLL_GSSFP_T	     * p_gssfp,
			   gss_cred_usage_t    p_usage,
			   gss_name_t	       p_name,
			   gss_name_t        * pp_name_ret  );

int   check_default_initiator_cred(
			   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   gss_name_t	     * pp_name_ret,
			   gss_buffer_t	       p_prname_ret,
			   gss_OID	     * pp_oid	    );


int   sap_acquire_cred(	   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   sc_variants_et      p_variante,
			   gss_cred_usage_t    p_usage,
			   gss_name_t	       p_in_name,
			   char		     * p_in_prname,
			   size_t	       p_in_prname_len,
			   gss_OID	       p_nametype,
			   OM_uint32	     * pp_lifetime,
			   gss_cred_id_t     * pp_cred,
			   OM_uint32	     * pp_maj_stat  );


int   printable_name_from_cred(
			   int		       p_trclevel,
			   DLL_GSSFP_T	     * p_gssfp,
			   gss_cred_id_t       p_cred,
			   ctx_type_et	       p_usagetype,
			   char		    ** pp_prname,
			   size_t	     * pp_prname_len,
			   gss_OID	     * pp_oid	    );


/********************************/
/*  buffers.c	-- Export list  */
/********************************/

int   release_buffer(	   DLL_GSSFP_T	     * p_gssfp,
			   gss_buffer_desc   * buf	    );

int   compare_buffers(	   int		       p_trclevel,
			   gss_buffer_t	       p_buffer1,
			   gss_buffer_t	       p_buffer2    );

void  print_buffer_head(   int		       p_trclevel,
			   char		     * p_name,
			   gss_buffer_t	       p_buffer     );

void  print_hexdump(	   unsigned char     * p_base,
			   size_t	       offset,
			   size_t	       p_num,
			   size_t	       p_align,
			   int		       p_show_ascii );

void  print_buffer_content(int		       p_trclevel,
			   gss_buffer_t	       p_buffer     );



/********************************/
/*  msg_prot.c	-- Export list  */
/********************************/

extern struct tmsg_job		 stdjob_xfer[];
extern struct tmsg_job		 stdjob_early_xfer[];
extern struct tmsg_job		 stdjob[];
extern struct tmsg_job		 xfer_only[];
extern struct defined_ranges_s	 defined_ranges[];


int   msg_prot_tests(	   DLL_GSSFP_T		 * p_gssfp_ini,
			   DLL_GSSFP_T		 * p_gssfp_acc	  );

void  msg_prot_statistics( size_t		   p_orimsg_size,
			   size_t		   p_out_size,
			   Ulong		   p_microsec,
			   struct xtime		 * p_xtime	  );

int   get_mic(		   int			   p_trclevel,
			   DLL_GSSFP_T		 * p_gssfp,
			   gss_ctx_id_t		   p_ctx,
			   gss_qop_t		   p_qop,
			   gss_buffer_t		   p_message,
			   gss_buffer_t		   p_mic_token,
			   OM_uint32		 * pp_maj_stat	  );

int   verify_mic(	   int			   p_trclevel,
			   DLL_GSSFP_T		 * p_gssfp,
			   gss_ctx_id_t		   p_ctx,
			   gss_buffer_t		   p_message,
			   gss_buffer_t		   p_mic_token,
			   gss_qop_t		 * pp_qop,
			   OM_uint32		 * pp_maj_stat	  );

int   wrap(		   int			   p_trclevel,
			   DLL_GSSFP_T		 * p_gssfp,
			   OM_uint32		   p_ctx_flags,
			   gss_ctx_id_t		   p_ctx,
			   gss_qop_t		   p_qop,
			   int			   p_conf_req,
			   gss_buffer_t		   p_message,
			   int			 * pp_conf,
			   gss_buffer_t		   p_wrap_token,
			   OM_uint32		 * pp_maj_stat	  );

int   unwrap(		   int			   p_trclevel,
			   DLL_GSSFP_T		 * p_gssfp,
			   OM_uint32		   p_ctx_flags,
			   int			   p_expect_conf,  /* confidentiality protection indicator expected */
			   int			   p_expect_zlm,   /* zero-length output message expected           */
			   gss_ctx_id_t		   p_ctx,
			   gss_buffer_t		   p_wrap_token,
			   gss_buffer_t		   p_message,
			   int			 * pp_conf,
			   gss_qop_t		 * pp_qop,
			   OM_uint32		 * pp_maj_stat	  );

int   wrap_size_limit(	   int			   p_trclevel,
			   DLL_GSSFP_T		 * p_gssfp,
			   gss_ctx_id_t		   p_ctx,
			   int			   p_conf_req,
			   gss_qop_t		   p_qop,
			   OM_uint32		   p_req_total,
			   OM_uint32		 * pp_max_input,
			   OM_uint32		 * pp_maj_stat	  );

int   max_wrap_size_limit( int			   p_trclevel,
			   struct range_list	 * p_ranges,
			   struct ctx_desc	 * p_ctx,
			   size_t		 * pp_min_conf,
			   size_t		 * pp_max_conf,
			   size_t		 * pp_min_integ,
			   size_t		 * pp_max_integ,
			   int			 * pp_success	  );

int   max_msg_increase(	   int			   p_trclevel,
			   struct range_list	 * p_ranges,
			   struct ctx_desc	 * p_ctx_a,
			   struct ctx_desc	 * p_ctx_b,
			   size_t		 * pp_min_conf,
			   size_t		 * pp_max_conf,
			   size_t		 * pp_bigmax_conf,
			   size_t		 * pp_min_integ,
			   size_t		 * pp_max_integ,
			   size_t		 * pp_bigmax_integ,
			   size_t		 * pp_min_mic,
			   size_t		 * pp_max_mic,
			   size_t		 * pp_bigmax_mic,
			   size_t		 * pp_max_len,
			   int			 * pp_success	  );


int   check_max_wrap_increase(
			   int			   p_trclevel,
			   OM_uint32		   p_flags,
			   DLL_GSSFP_T		 * p_gssfp_ini,
			   DLL_GSSFP_T		 * p_gssfp_acc	  );


int   queue_flush(	   struct tmsg_entry	** pp_queue    );

void  queue_add(	   tmsg_type_et		   p_type,
			   gss_qop_t		   p_qop,
			   struct tmsg_entry	** pp_entry,
			   struct tmsg_entry	** pp_queue    );

struct tmsg_entry *
      queue_remove(	   struct tmsg_entry	** pp_queue    );

struct tmsg_entry *
      queue_new_entry(	   size_t		   p_size      );

int   tstm_process_entry(  struct ctx_desc	* p_ctx,
			   struct tmsg_entry	* p_entry,
			   OM_uint32		* pp_maj_stat  );

int   test_message_exchange(
			   int			  p_trclevel,
			   char			* p_test_title,
			   int			  p_timing,
			   struct tmsg_job	* p_job,
			   struct ctx_desc     ** pp_ini,
			   struct ctx_desc     ** pp_acc,
			   struct tmsg_entry   ** pp_queue_ini,
			   struct tmsg_entry   ** pp_queue_acc,
			   int			* pp_success   );


int   sap_msg_exchange(	   int			   p_trclevel,
			   OM_uint32		   p_flags,
			   OM_uint32		   p_lifetime,
			   struct tmsg_job	 * p_job,
			   DLL_GSSFP_T		 * p_gssfp_ini,
			   DLL_GSSFP_T		 * p_gssfp_acc,
			   sc_variants_et	   p_ini_cred_type,
			   sc_variants_et	   p_acc_cred_type,
			   char			 * p_target,
			   size_t		   p_target_len,
			   int			 * pp_success  );


int   benchmark_msgprot(   int			   p_trclevel,
			   DLL_GSSFP_T		*  p_gssfp,
			   int			   atob,
			   int			   p_type,
			   size_t		   p_size      );


int   msg_prot_test(	   int			   p_trclevel,
			   OM_uint32		   p_flags,
			   OM_uint32		   p_lifetime,
			   char			 * p_test_title,
			   mp_test_et		   p_mptype,
			   DLL_GSSFP_T		 * p_gssfp_ini,
			   DLL_GSSFP_T		 * p_gssfp_acc,
			   sc_variants_et	   p_ini_cred_type,
			   sc_variants_et	   p_acc_cred_type,
			   void			 * p_target,
			   size_t		   p_target_len,
			   int			 * pp_success	  );

int   do_msg_prot_test(	   int			   p_trclevel,
			   OM_uint32		   p_flags,
			   OM_uint32		   p_lifetime,
			   char			 * p_test_name,
			   mp_test_et		   p_mptype,
			   DLL_GSSFP_T		 * p_gssfp_ini,
			   DLL_GSSFP_T		 * p_gssfp_acc,
			   int			 * pp_success	  );

/********************************/
/*  generic.c	-- Export list  */
/********************************/

extern char * gss_call_names[GSS_CALL_ENUM_MAX];

int   generic_tests(	DLL_GSSFP_T	  * p_gssfp	 );

int   print_status(	DLL_GSSFP_T	  * p_gssfp,
		        gss_call_et	    call_enum,
			OM_uint32	    major_status,
			OM_uint32	    minor_status );

void  print_lifetime_only(
			char		  * p_buffer,
			OM_uint32	    p_lifetime	 );

void  print_lifetime(	int		    p_trclevel,
			char		  * prefix,
			OM_uint32	    p_lifetime	 );

int   check_lifetime_change( int	    p_trclevel,
			time_t		    p_enter,
			OM_uint32	    p_lifetime1,
			OM_uint32	    p_lifetime2	 );

int   display_status(	int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp,
			OM_uint32	    p_status_value,
			int		    p_status_type,
			gss_OID		    p_oid,
			OM_uint32	  * pp_context,
			gss_buffer_t	    p_message,
			OM_uint32	  * pp_maj_stat	 );

int   indicate_mechs(	int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp,
			gss_OID_set	  * pp_oid_set,
			OM_uint32	  * pp_maj_stat	 );

int   inquire_names_for_mech(
			int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp,
			gss_OID_set	  * pp_nt_list,
			OM_uint32	  * pp_maj_stat	 );



/********************************/
/*  filexfer.c	-- Export list  */
/********************************/

struct xfer_ctx_s {
   gss_buffer_desc	     exp_ctx;
   gss_OID_desc		     ctx_mech;
   gss_buffer_desc	     ini_prname;
   gss_buffer_desc	     ini_xpname;
   gss_buffer_desc	     acc_prname;
   gss_buffer_desc	     acc_xpname;
   gss_OID_desc		     can_nt;
   time_t		     enter;
   OM_uint32		     lifetime;
   OM_uint32		     lifetime_req;
   OM_uint32		     flags;
   OM_uint32		     flags_req;
   OM_uint32		     qop;
   OM_uint32		     rci;
   int			     initiator;
   sc_variants_et	     cred_type;
};



typedef enum xp_object_e {

      XP_INVALID      =  0,
      XP_CONTEXT_INI  =  1,	/* gss_buffer_t   */
      XP_CONTEXT_ACC  =  2,	/* gss_buffer_t	  */
      XP_PRNAME_INI   =  3,	/* gss_buffer_t   */
      XP_PRNAME_ACC   =  4,	/* gss_buffer_t   */
      XP_XPNAME_INI   =  5,	/* gss_buffer_t   */
      XP_XPNAME_ACC   =  6,	/* gss_buffer_t   */
      XP_CRED_TYPE    =  7,	/* sc_variants_et */
      XP_QOP	      =  8,	/* OM_uint32	  */
      XP_LIFETIME     =  9,	/* OM_uint32	  */
      XP_LIFETIME_REQ = 10,	/* OM_uint32	  */
      XP_FLAGS	      = 11,	/* OM_uint32	  */
      XP_FLAGS_REQ    = 12,	/* OM_uint32	  */
      XP_TIME	      = 13,	/* OM_uint32	  */
      XP_OID_MECH     = 14,	/* gss_OID	  */
      XP_OID_NT	      = 15,	/* gss_OID	  */
      XP_TERMINATOR   = 16,	/* nothing, a terminator */
      XP_TMSG_JOBLIST = 17,
      XP_RCI	      = 18      /* OM_uint32	  */

} xp_object_et;



#define STORE_UINT16_MSB(value,ptr)					\
      ( ((Uchar *)ptr)[0] = (Uchar)((((Ushort)value)>>8)&0xff),		\
        ((Uchar *)ptr)[1] = (Uchar)(((Ushort)value) & 0xff) )

#define STORE_UINT32_MSB(value,ptr)					\
      ( ((Uchar *)ptr)[0] = (Uchar)((((OM_uint32)value)>>24)&0xff),     \
        ((Uchar *)ptr)[1] = (Uchar)((((OM_uint32)value)>>16)&0xff),     \
        ((Uchar *)ptr)[2] = (Uchar)((((OM_uint32)value)>> 8)&0xff),     \
        ((Uchar *)ptr)[3] = (Uchar)   (value & 0xff)                 )

#define LOAD_UINT16_MSB(ptr)                                            \
      ( (Ushort)(((Uchar *)ptr)[0]<<8) + ((Uchar *)ptr)[1] )

#define LOAD_UINT32_MSB(ptr)                                            \
      ( (OM_uint32)(((Uchar *)ptr)[0]<<24) + (((Uchar *)ptr)[1]<<16)    \
                 + (((Uchar *)ptr)[2]<<8)  + ((Uchar *)ptr)[3]      )


int   write_to_file(	int		    p_trclevel,
			FILE	          * p_fp,
			int		    p_initiator,
			struct ctx_desc   * ctx,
			int		  * pp_success	    );


int   export_to_file(	int                 p_trclevel,
			char	          * p_filename,
			struct tmsg_job   * p_joblist,
			int		    p_rci,
			struct ctx_desc	 ** pp_ini,
			struct ctx_desc  ** pp_acc,
			int	          * pp_success	    );


int   import_from_file( int		    p_trclevel,
			char		  * p_filename,
			int		    p_copy_names,
			struct tmsg_job	 ** pp_joblist,
			DLL_GSSFP_T       * p_gssfp_ini,
			DLL_GSSFP_T	  * p_gssfp_acc,
			struct ctx_desc	 ** pp_ini,
			struct ctx_desc  ** pp_acc,
			int		  * pp_rci,
			int		  * pp_success	    );


int   write_object(	int		    p_trclevel,
			FILE		  * p_fp,
			xp_object_et	    p_object_type,
			void		  * p_object,
			size_t		    p_object_len    );


int   read_from_file(	int		     p_trclevel,
			FILE	           * p_fp,
			char		   * p_filename,
			struct xfer_ctx_s ** pp_xfer_ctx,
			struct tmsg_job   ** pp_joblist	    );


void  free_xfer_ctx(	struct xfer_ctx_s ** pp_xc	    );


int   transfer_via_file(
			int		    p_trclevel,
			char		  * p_filename,
			struct tmsg_job	  * p_joblist,
			struct ctx_desc	 ** pp_ini,
			struct ctx_desc	 ** pp_acc,
			int	          * pp_success	    );


int   transfer_via_child(
			int		    p_trclevel,
			struct tmsg_job   * p_joblist,
			struct ctx_desc  ** pp_ini,
			struct ctx_desc  ** pp_acc,
			int		  * pp_success	    );


int   write_single_option(
			FILE		  * p_fp,
			char		  * p_filename,
			int		    p_opt_type,
			int		    p_option,
			void		  * p_opt_val,
			size_t		    p_opt_len	    );

int   write_options(	FILE		  * p_fp,
			char		  * p_filename	    );

int   write_options_to_file(
			char		  * p_filename	    );

int   read_single_option(
			FILE		  * p_fp,
			char		  * p_filename,
			int		  * pp_opt,
			int		  * pp_opt_type,
			void		 ** pp_opt_val,
			size_t		  * pp_opt_len	    );

int   read_options(	FILE		  * p_fp,
			char		  * p_filename	    );

int   read_options_from_file(
			char		  * p_filename	    );





/********************************/
/*  timer.c	-- Export list  */
/********************************/

extern char           * hrtimer_name;
extern unsigned long    hrtimer_resolution;

void	      init_timer(  void );
void	      start_timer( void );
unsigned long read_timer(  void );
char *        sprint_timer( unsigned long timer_val );
void	      show_timer_resolution( void );

void  print_timing_statistics(
			int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp	 );

void  clear_timing_data(int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp,
			gss_call_et	    first_call,
			gss_call_et	    last_call	 );

void  print_timing_data(
			int		    p_trclevel,
			DLL_GSSFP_T	  * p_gssfp,
			char		  * p_headline,
			gss_call_et	    first_call,
			gss_call_et	    last_call,
			int		    clear_flag );


Ulong	      sample_avg( Ulong * p_sample, size_t p_nelements );




/********************************/
/*  platform.c	-- Export list  */
/********************************/

void	       sys_greeting( char * p_prefix,  struct sys_platform_s * p_pls );

void	       sys_machine_speed( Ulong * dbg_speed, Ulong * opt_speed );

char *	       sys_get_hostname( void );

#define BENCH_MEMSIZE        10000
#define PENTIUM90_SPEED_DBG   3560  /* for BENCH_MEMSIZE=10000, Win32-Debug,   Visual C++ 5 */
#define PENTIUM90_SPEED_OPT   1854  /* for BENCH_MEMSIZE=10000, Win32-Release, Visual C++ 5 */

extern float  perf_correction;

extern char * os_platform;


/********************************/
/*  md5.c -- Export list        */
/********************************/
typedef struct {
  Uint32        state[4];                           /* state (ABCD)    */
  Uint32        count[2];  /* number of bits, modulo 2^64 (lsb first)  */
  unsigned char buffer[64];                         /* input buffer    */
} haMD5_CTX;


void haMD5Init   ( haMD5_CTX * context );	 /* in/out: context    */

void haMD5Update ( haMD5_CTX      * context,	 /* in: context        */
		   unsigned char  * input,       /* in: inputBuffer    */
		   size_t           inputLen );	 /* in: inputLen       */

void haMD5Final  ( unsigned char    digest[16],	 /* in/out: MD5-digest */ 
		   haMD5_CTX        * context ); /* in:     context    */



/********************************/
/* errors.c -- Export list      */
/********************************/
extern char   * bad_target_name;

struct dspname_test_s {
   OM_uint32    status_value;
   char       * error_name;
   int	        may_fail;
};


int   error_tests(	      DLL_GSSFP_T	      * p_gssfp_ini,
			      DLL_GSSFP_T	      * p_gssfp_acc	);

int   errors_with_display_status(
			      DLL_GSSFP_T	      * p_gssfp		);

int   test_display_status(
			      int		        p_trclevel,
			      DLL_GSSFP_T	      * p_gssfp,
			      struct dspname_test_s   * p_test_liste,
			      Ulong		      * pp_maxlines,
			      size_t		      * pp_min_linelen,
			      size_t		      * pp_max_linelen,
			      size_t		      * pp_sum_linelen,
			      Ulong		      * pp_counter	);

int   errors_with_names(      DLL_GSSFP_T	      * p_gssfp		);

int   errors_with_creds(      DLL_GSSFP_T	      * p_gssfp_ini,
			      DLL_GSSFP_T	      * p_gssfp_acc	);

int   errors_with_contexts(   DLL_GSSFP_T	      * p_gssfp_ini,
			      DLL_GSSFP_T	      * p_gssfp_acc	);


/*********************************************/
/* load_dll.c / link_lib.c  --  Export list  */
/*********************************************/

extern int dll_dynamic_linking;


#endif /* _GSSTEST_H_ */


