/* Process model C form file: internalHLRProc.pr.c */
/* Portions of this file copyright 1986-2010 by OPNET Technologies, Inc. */


/*
 =========================== NOTE ==========================
 This file is automatically generated from internalHLRProc.pr.m
 during a process model compilation.

 Do NOT manually edit this file.
 Manual edits will be lost during the next compilation.
 =========================== NOTE ==========================
*/



/* This variable carries the header into the object file */
const char internalHLRProc_pr_c [] = "MIL_3_Tfile_Hdr_ 160A 30A op_runsim_dev 7 516CFDAC 516CFDAC 1 esl2-10 skathire 0 0 none none 0 0 none 0 0 0 0 0 0 0 0 2871 6                                                                                                                                                                                                                                                                                                                                                                                                   ";
#include <string.h>



/* OPNET system definitions */
#include <opnet.h>



/* Header Block */

#include "msRecord.h"

#define INTERNAL_HLR_RCV_IN_STRM 0
#define INTERNAL_HLR_XMT_OUT_STRM 0
#define NUM_OF_MS_RECORDS 100


/* transition macros */
#define GET_REQ_FROM_SGSN (op_intrpt_type () == \
OPC_INTRPT_STRM && op_intrpt_strm () == INTERNAL_HLR_RCV_IN_STRM)

/* End of Header Block */

#if !defined (VOSD_NO_FIN)
#undef	BIN
#undef	BOUT
#define	BIN		FIN_LOCAL_FIELD(_op_last_line_passed) = __LINE__ - _op_block_origin;
#define	BOUT	BIN
#define	BINIT	FIN_LOCAL_FIELD(_op_last_line_passed) = 0; _op_block_origin = __LINE__;
#else
#define	BINIT
#endif /* #if !defined (VOSD_NO_FIN) */



/* State variable definitions */
typedef struct
	{
	/* Internal state tracking for FSM */
	FSM_SYS_STATE
	/* State Variables */
	char	                   		debugStr[1000]                                  ;
	MSRecord	               		msRecordArray[100]                              ;	/* Stimulate the HLR stored information and will return the MS */
	                        		                                                	/* record information to SGSN upon request.                    */
	} internalHLRProc_state;

#define debugStr                		op_sv_ptr->debugStr
#define msRecordArray           		op_sv_ptr->msRecordArray

/* These macro definitions will define a local variable called	*/
/* "op_sv_ptr" in each function containing a FIN statement.	*/
/* This variable points to the state variable data structure,	*/
/* and can be used from a C debugger to display their values.	*/
#undef FIN_PREAMBLE_DEC
#undef FIN_PREAMBLE_CODE
#define FIN_PREAMBLE_DEC	internalHLRProc_state *op_sv_ptr;
#define FIN_PREAMBLE_CODE	\
		op_sv_ptr = ((internalHLRProc_state *)(OP_SIM_CONTEXT_PTR->_op_mod_state_ptr));


/* No Function Block */

#if !defined (VOSD_NO_FIN)
enum { _op_block_origin = __LINE__ };
#endif

/* Undefine optional tracing in FIN/FOUT/FRET */
/* The FSM has its own tracing code and the other */
/* functions should not have any tracing.		  */
#undef FIN_TRACING
#define FIN_TRACING

#undef FOUTRET_TRACING
#define FOUTRET_TRACING

#if defined (__cplusplus)
extern "C" {
#endif
	void internalHLRProc (OP_SIM_CONTEXT_ARG_OPT);
	VosT_Obtype _op_internalHLRProc_init (int * init_block_ptr);
	void _op_internalHLRProc_diag (OP_SIM_CONTEXT_ARG_OPT);
	void _op_internalHLRProc_terminate (OP_SIM_CONTEXT_ARG_OPT);
	VosT_Address _op_internalHLRProc_alloc (VosT_Obtype, int);
	void _op_internalHLRProc_svar (void *, const char *, void **);


#if defined (__cplusplus)
} /* end of 'extern "C"' */
#endif




/* Process model interrupt handling procedure */


void
internalHLRProc (OP_SIM_CONTEXT_ARG_OPT)
	{
#if !defined (VOSD_NO_FIN)
	int _op_block_origin = 0;
#endif
	FIN_MT (internalHLRProc ());

		{
		/* Temporary Variables */
		Packet * pkptr;
		/* End of Temporary Variables */


		FSM_ENTER ("internalHLRProc")

		FSM_BLOCK_SWITCH
			{
			/*---------------------------------------------------------*/
			/** state (init) enter executives **/
			FSM_STATE_ENTER_FORCED_NOLABEL (0, "init", "internalHLRProc [init enter execs]")
				FSM_PROFILE_SECTION_IN ("internalHLRProc [init enter execs]", state0_enter_exec)
				{
				List* internalHLRListPtr;
				List* subscribedInfoListPtr;
				int numRows, i;
				int imsi;
				char* apn;
				int qosReliablityClass, qosDelayClass, qosPrecedenceClass;
				int qosPeakBitRate, qosMeanBitRate, pdpType;
				char* pdpAddress; 
				QoS qosSubscribedStruct;
				PDPAddress pdpAddressStruct;
				APN apnStruct;
				
				// initialize the state variables: msRecords
				for (i=0; i < NUM_OF_MS_RECORDS; i++)
					{
					  msRecordArray[i].isSet = 0;
					}
				
				
				// open and read the InternalHLR.gdf file which consists
				// the MM context and PDP contexts of the MS subscribers
				
				internalHLRListPtr = op_prg_gdf_read ("InternalHLR");
				
				/* determine how many entries the file consists */
				numRows = op_prg_list_size(internalHLRListPtr);
				
				for (i=0; i < numRows; i++)
					{
					// obtain a list of the columnar fields in each row
					subscribedInfoListPtr = op_prg_str_decomp(op_prg_list_access(internalHLRListPtr, i), ",");
					
					// extract the values of the two fields, and put them into state variables
					imsi = atoi(op_prg_list_access (subscribedInfoListPtr,0));
					apn = op_prg_list_access (subscribedInfoListPtr,1);
					qosReliablityClass = atoi(op_prg_list_access (subscribedInfoListPtr,2));
					qosDelayClass = atoi(op_prg_list_access (subscribedInfoListPtr,3));
					qosPrecedenceClass = atoi(op_prg_list_access (subscribedInfoListPtr,4));
					qosPeakBitRate = atoi(op_prg_list_access (subscribedInfoListPtr,5));
					qosMeanBitRate = atoi(op_prg_list_access (subscribedInfoListPtr,6));
					pdpType = atoi(op_prg_list_access (subscribedInfoListPtr,7));
					pdpAddress = op_prg_list_access (subscribedInfoListPtr,8);
					
					msRecordArray[imsi].isSet = 1;
					
					qosSubscribedStruct.reliabilityClass = qosReliablityClass;
					qosSubscribedStruct.delayClass = qosDelayClass;
					qosSubscribedStruct.precedenceClass = qosPrecedenceClass;
					qosSubscribedStruct.peakBitRate = qosPeakBitRate;
					qosSubscribedStruct.meanBitRate = qosMeanBitRate;
					msRecordArray[imsi].qosSubscribed = qosSubscribedStruct;
					
					memset(pdpAddressStruct.pdpAddressValue, '\0', 16);
					pdpAddressStruct.pdpType = pdpType;
					strncpy(pdpAddressStruct.pdpAddressValue, pdpAddress, strlen(pdpAddress)+1);
					msRecordArray[imsi].pdpAddress = pdpAddressStruct;
					
					memset(apnStruct.apnNetworkID, '\0', 64);
					strncpy(apnStruct.apnNetworkID, apn, strlen(apn)+1);
					msRecordArray[imsi].apn = apnStruct;
					
					/*
					sprintf (debugStr, "Retrieve HLR Record %d. IMSI %d", i, imsi);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. APN %s", i, msRecordArray[imsi].apn.apnNetworkID);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. QoS Reliability %d", i, msRecordArray[imsi].qosSubscribed.reliabilityClass);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. QoS Delay %d", i, msRecordArray[imsi].qosSubscribed.delayClass);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. QoS Precedence %d", i, msRecordArray[imsi].qosSubscribed.precedenceClass);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. QoS Peak Bit Rate %d", i, msRecordArray[imsi].qosSubscribed.peakBitRate);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. QoS Mean Bit Rate %d", i, msRecordArray[imsi].qosSubscribed.meanBitRate);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. PDP Type %d", i, msRecordArray[imsi].pdpAddress.pdpType);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					sprintf (debugStr, "Retrieve HLR Record %d. PDP Address %s", i, msRecordArray[imsi].pdpAddress.pdpAddressValue);
				    op_prg_odb_print_major ("Debug message for Internal HLR", debugStr, OPC_NIL);
					*/
					
					
					// deallocate the subscribedInfo list contents and list
					op_prg_list_free(subscribedInfoListPtr);
					op_prg_mem_free(subscribedInfoListPtr);
					}
				// deallocate the internal HLR list contents and list
				op_prg_list_free(internalHLRListPtr);
				op_prg_mem_free(internalHLRListPtr);
				}
				FSM_PROFILE_SECTION_OUT (state0_enter_exec)

			/** state (init) exit executives **/
			FSM_STATE_EXIT_FORCED (0, "init", "internalHLRProc [init exit execs]")


			/** state (init) transition processing **/
			FSM_TRANSIT_FORCE (1, state1_enter_exec, ;, "default", "", "init", "idle", "tr_0", "internalHLRProc [init -> idle : default / ]")
				/*---------------------------------------------------------*/



			/** state (idle) enter executives **/
			FSM_STATE_ENTER_UNFORCED (1, "idle", state1_enter_exec, "internalHLRProc [idle enter execs]")

			/** blocking after enter executives of unforced state. **/
			FSM_EXIT (3,"internalHLRProc")


			/** state (idle) exit executives **/
			FSM_STATE_EXIT_UNFORCED (1, "idle", "internalHLRProc [idle exit execs]")
				FSM_PROFILE_SECTION_IN ("internalHLRProc [idle exit execs]", state1_exit_exec)
				{
				int intrpt_type;
				
				/* Determine the interrupt type as the model perform .	*/
				/*
				intrpt_type = op_intrpt_type ();
				if (intrpt_type == OPC_INTRPT_ENDSIM)
					{
					sprintf (debugStr, "EndSim received");
				    op_prg_odb_print_major ("Debug message for HLR", 
						debugStr, OPC_NIL);	
					}
				*/
				}
				FSM_PROFILE_SECTION_OUT (state1_exit_exec)


			/** state (idle) transition processing **/
			FSM_PROFILE_SECTION_IN ("internalHLRProc [idle trans conditions]", state1_trans_conds)
			FSM_INIT_COND (GET_REQ_FROM_SGSN)
			FSM_DFLT_COND
			FSM_TEST_LOGIC ("idle")
			FSM_PROFILE_SECTION_OUT (state1_trans_conds)

			FSM_TRANSIT_SWITCH
				{
				FSM_CASE_TRANSIT (0, 2, state2_enter_exec, ;, "GET_REQ_FROM_SGSN", "", "idle", "getRequestRcv", "tr_3", "internalHLRProc [idle -> getRequestRcv : GET_REQ_FROM_SGSN / ]")
				FSM_CASE_TRANSIT (1, 1, state1_enter_exec, ;, "default", "", "idle", "idle", "tr_4_0", "internalHLRProc [idle -> idle : default / ]")
				}
				/*---------------------------------------------------------*/



			/** state (getRequestRcv) enter executives **/
			FSM_STATE_ENTER_FORCED (2, "getRequestRcv", state2_enter_exec, "internalHLRProc [getRequestRcv enter execs]")
				FSM_PROFILE_SECTION_IN ("internalHLRProc [getRequestRcv enter execs]", state2_enter_exec)
				{
				
				int imsi, result;
				Packet * getInternalHLRInfoResponsePkPtr;
				APN *apnStructPtr;
				QoS *qosSubscribedStructPtr;
				PDPAddress *pdpAddressStructPtr;
				
				pkptr = op_pk_get(INTERNAL_HLR_RCV_IN_STRM);
				
				// retrieve the IMSI from the request which is
				// the key for the Internal HLR database
				// Note: IMSI is the index to the state variable: msStructArray
				
				op_pk_nfd_get (pkptr, "imsi", &imsi);
				
				// reply SGSN with the search result
				getInternalHLRInfoResponsePkPtr = op_pk_create_fmt ("GetInternalHLRInfoResponse");
				
				if (msRecordArray[imsi].isSet == 0)
					{
					result = RECORD_NOT_FOUND;
					op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "result", result);
					op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "imsi", imsi);
					}
				else
				    {
					result = RECORD_FOUND;
				    op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "result", result);
					op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "imsi", imsi);
					
					// allocate a new data structure for APN
					apnStructPtr = (APN *) op_prg_mem_alloc (sizeof (APN));
				    // set the apn value
				    strncpy(apnStructPtr->apnNetworkID, msRecordArray[imsi].apn.apnNetworkID, 
						strlen(msRecordArray[imsi].apn.apnNetworkID)+1);
				       
					// assign the data structure to apn field in the packet
				    op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "apn", apnStructPtr,
				        op_prg_mem_copy_create, op_prg_mem_free, sizeof (APN));
					
					// allocate a new data structure for PDP Address
					pdpAddressStructPtr = (PDPAddress *) op_prg_mem_alloc (sizeof (PDPAddress));
				    
					// set the pdpAddress value
				    strncpy(pdpAddressStructPtr->pdpAddressValue, msRecordArray[imsi].pdpAddress.pdpAddressValue, 
						strlen(msRecordArray[imsi].pdpAddress.pdpAddressValue)+1);
					// set the pdpAddress type
					pdpAddressStructPtr->pdpType = msRecordArray[imsi].pdpAddress.pdpType;
				       
					// assign the data structure to pdpAddress field in the packet
				    op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "pdpAddress", pdpAddressStructPtr,
				        op_prg_mem_copy_create, op_prg_mem_free, sizeof (PDPAddress));
					
					// allocate a new data structure for QoS Subscribed
					qosSubscribedStructPtr = (QoS *) op_prg_mem_alloc (sizeof (QoS));
				    // set the attribute of the QoS subscribed
					qosSubscribedStructPtr->reliabilityClass = msRecordArray[imsi].qosSubscribed.reliabilityClass;
					qosSubscribedStructPtr->delayClass = msRecordArray[imsi].qosSubscribed.delayClass;
					qosSubscribedStructPtr->precedenceClass = msRecordArray[imsi].qosSubscribed.precedenceClass;
					qosSubscribedStructPtr->peakBitRate = msRecordArray[imsi].qosSubscribed.peakBitRate;
					qosSubscribedStructPtr->meanBitRate = msRecordArray[imsi].qosSubscribed.meanBitRate;
					
					// assign the data structure to qos field in the packet
				    op_pk_nfd_set(getInternalHLRInfoResponsePkPtr, "qos", qosSubscribedStructPtr,
				        op_prg_mem_copy_create, op_prg_mem_free, sizeof (QoS));
					
				    }
				op_pk_send(getInternalHLRInfoResponsePkPtr, INTERNAL_HLR_XMT_OUT_STRM);
				
				}
				FSM_PROFILE_SECTION_OUT (state2_enter_exec)

			/** state (getRequestRcv) exit executives **/
			FSM_STATE_EXIT_FORCED (2, "getRequestRcv", "internalHLRProc [getRequestRcv exit execs]")


			/** state (getRequestRcv) transition processing **/
			FSM_TRANSIT_FORCE (1, state1_enter_exec, ;, "default", "", "getRequestRcv", "idle", "tr_4", "internalHLRProc [getRequestRcv -> idle : default / ]")
				/*---------------------------------------------------------*/



			}


		FSM_EXIT (0,"internalHLRProc")
		}
	}




void
_op_internalHLRProc_diag (OP_SIM_CONTEXT_ARG_OPT)
	{
	/* No Diagnostic Block */
	}




void
_op_internalHLRProc_terminate (OP_SIM_CONTEXT_ARG_OPT)
	{

	FIN_MT (_op_internalHLRProc_terminate ())


	/* No Termination Block */

	Vos_Poolmem_Dealloc (op_sv_ptr);

	FOUT
	}


/* Undefine shortcuts to state variables to avoid */
/* syntax error in direct access to fields of */
/* local variable prs_ptr in _op_internalHLRProc_svar function. */
#undef debugStr
#undef msRecordArray

#undef FIN_PREAMBLE_DEC
#undef FIN_PREAMBLE_CODE

#define FIN_PREAMBLE_DEC
#define FIN_PREAMBLE_CODE

VosT_Obtype
_op_internalHLRProc_init (int * init_block_ptr)
	{
	VosT_Obtype obtype = OPC_NIL;
	FIN_MT (_op_internalHLRProc_init (init_block_ptr))

	obtype = Vos_Define_Object_Prstate ("proc state vars (internalHLRProc)",
		sizeof (internalHLRProc_state));
	*init_block_ptr = 0;

	FRET (obtype)
	}

VosT_Address
_op_internalHLRProc_alloc (VosT_Obtype obtype, int init_block)
	{
#if !defined (VOSD_NO_FIN)
	int _op_block_origin = 0;
#endif
	internalHLRProc_state * ptr;
	FIN_MT (_op_internalHLRProc_alloc (obtype))

	ptr = (internalHLRProc_state *)Vos_Alloc_Object (obtype);
	if (ptr != OPC_NIL)
		{
		ptr->_op_current_block = init_block;
#if defined (OPD_ALLOW_ODB)
		ptr->_op_current_state = "internalHLRProc [init enter execs]";
#endif
		}
	FRET ((VosT_Address)ptr)
	}



void
_op_internalHLRProc_svar (void * gen_ptr, const char * var_name, void ** var_p_ptr)
	{
	internalHLRProc_state		*prs_ptr;

	FIN_MT (_op_internalHLRProc_svar (gen_ptr, var_name, var_p_ptr))

	if (var_name == OPC_NIL)
		{
		*var_p_ptr = (void *)OPC_NIL;
		FOUT
		}
	prs_ptr = (internalHLRProc_state *)gen_ptr;

	if (strcmp ("debugStr" , var_name) == 0)
		{
		*var_p_ptr = (void *) (prs_ptr->debugStr);
		FOUT
		}
	if (strcmp ("msRecordArray" , var_name) == 0)
		{
		*var_p_ptr = (void *) (prs_ptr->msRecordArray);
		FOUT
		}
	*var_p_ptr = (void *)OPC_NIL;

	FOUT
	}

