/* 
** CDMA 2000 project, SMPP module
**
** File name: smpp.h
** Written by Li Long at 2004-11-25
** CVS $Id: smpp.h,v0.1 2004/11/25 17:03:14 lilong Exp $
**
*/
#ifndef	_SMPP_h
#define	_SMPP_h


#include "smpp_public.h"
#include "smpp_const.h"
#include "../../../debug/src/include/debug.h"
#include "../../../sccp/src/include/sccp.h"
#include "../../../iptrans/src/include/iptrans.h"
#include "../../../mtp3/src/include/mtp3.h"
#include "../../../snmp/src/include/snmp.h"
#include "../../../public/src/include/public.h"

#include "smpp_msg.h"

enum SMPP_State_Constant {INIT, IDLE, WAITING, ESTABLISHED, SUSPEND};
enum SMPP_APIEvent {APIEventReversed, Register, Setup, Close};
enum SMPP_InterEvent {InterEventReserved, Outbind, Unbind, UnbindResp, 
	BindTransmitter, BindReceiver, BindTransceiver,	//4
	BindTransmitterResp, BindReceiverResp, BindTransceiverResp, //7
	EnquireLink, EnquireLinkResp, //10
	SubmitSM, SubmitSMResp, //12
	SubmitMulti, SubmitMultiResp, //14
	DeliverSM, DeliverSMResp, //16
	DataSM, DataSMResp, //18
	GenericNak, //20
	SessionInitTimeout, EnquireLinkTimeout, InactivityTimeout, ResponseTimeOut, //21
	QuerySM, QuerySMResp, //25
	CancelSM, CancelSMResp, 	//27
	ReplaceSM, ReplaceSMResp, 	//29
	AlertNotification, //31
	UnknownCommandID}; //32

typedef struct SMPP_LINK
{
	DWORD	seq_num;
	DWORD	command_status;
}SMPP_LINK;

typedef struct SMPP_DEBUG_STRUCT
{
	BYTE	debug_switch;
	BYTE	link_switch[MAX_SMPP_LINK];
}SMPP_DEBUG_STRUCT;

typedef struct SMPP_PARAM
{
	BYTE	link_no;	//0~31
	BYTE	link_enable;	//0-Disable, 1-Enable
	BYTE	link_type;		//0-UDP 1-TCP
	BYTE	server_type;	//0-SMPP_CLIENT; 1-SMPP_SERVER
	BYTE	session_type;	//0-BIND_TX; 1-BIND_RX; 2-BIND_TRX
	char	sys_id[16];
	char	password[9];
	char	system_type[13];
	char	localGTT[16];
	char	remoteGTT[16];
	DWORD	local_ip;
	DWORD	remote_ip;
	DWORD	session_init_timer;
	DWORD	enquire_link_timer;
	DWORD	inactivity_timer;
	DWORD	response_timer;
	char	service_number[8];
	BYTE	localSSN;
	BYTE	remoteSSN;	
	BYTE	message_mode;
} SMPP_PARAM;

// Inter-Function define
int smpp_Register(BYTE);
void smpp_PrimitiveSend(int linkNo, int command_id);

void smpp_initTCPClient();
void smpp_initTCPServer();
void smpp_tcp_connect(int link);
void smpp_debugInit();
void smpp_stateInit();
void smpp_msgInit();
void smpp_debugTimer();
char *smpp_getLocalIP();
void smpp_setupTCPLink(int);
void smpp_rvMsgOverSCCP(BYTE sccp_usertype);
void smpp_rvMsgOverTCP();
WORD smpp_getServerPort();
DWORD smpp_getSequenceNumber(int);
int smpp_decode_msg(int, SMPP_GENERAL*, int);
int smpp_closeTCPConnection(int);
int smpp_encode_msg(int, SMPP_MSG *, int);
void smpp_setSccpAddr(int, SCCP_ADDR *, SCCP_ADDR *);
BYTE smpp_ascii2GTAI(BYTE *pGTAI, char *pGTT);
void smpp_GTAI2ascii(char *, BYTE *, BYTE);
void smpp_send_ascout(char *);
void smpp_send_error(char *);
void smpp_display_hex_msg(BYTE* disp_ptr, int len);
void smpp_command_id_to_string(char *comm_str, DWORD command_id);
void smpp_command_status_to_string(char* status_str, DWORD command_status);
void smpp_ton_to_string(char* ton_str, BYTE ton);
void smpp_npi_to_string(char* npi_str, BYTE npi);

void smpp_sendBindResp(int, int, DWORD command_status);
void smpp_sendUnbind(int);
void smpp_sendUnbindResp(int);
void smpp_sendEnquireLink(int);
void smpp_sendEnquireLinkResp(int);
void smpp_sendOutbind(int);
void smpp_sendBind(int, int);
void smpp_sendGenericNack(int, DWORD, DWORD);
void smpp_sendResponse(int , DWORD , DWORD , DWORD );

void smpp_addTLV(BYTE *, WORD, BYTE *, WORD);

int smpp_loadParam();
int smpp_writeParam();
void smpp_checkParam();
int smpp_setParam(DWORD *oid, BYTE *pdata, WORD datalen);
void smpp_reset();
void smpp_debug(DWORD mask, const char *fmt, ...);
void smpp_close(BYTE linkNo);
void smpp_mibInit();
int smpp_decode_optional_parameter(SMPP_OPTIONAL_PARAMETER* opt_ptr, BYTE* msg_ptr, int t_len);
int smpp_check_sysid_route(char* sysid_rv, BYTE sysidlen_rv, BYTE server_type, BYTE session_type);
int smpp_decode_setup(BYTE link_type, int tcp_linkNo, BYTE src_ref, SMPP_GENERAL *pData, int len);

/* TCP connection */
typedef struct SocketsMsg
{
	int AcceptNum;
	int ReadNum;
	int ReadQueue[MAX_SMPP_LINK];
	int WriteNum;
	int WriteQueue[MAX_SMPP_LINK];
	int ExceptNum;
	int ExceptQueue[MAX_SMPP_LINK];
}SocketsMsg;

typedef struct SocketsInUse
{
	int DaemonSock;
	int SockNum;
	int Sockets[MAX_SMPP_LINK];
	int client_sock[MAX_SMPP_LINK];
	int	server_sock[MAX_SMPP_LINK];
	u32	remote_ip[MAX_SMPP_LINK];	
	fd_set readfds,writefds,exceptfds;
	int Port;
}SocketsInUse;

//SocketsMsg SockMsg;
int QuerySocketsMsg();

// Call back function define
//param1:linkNo; param2:msg mode; param3: pData; param4:pDataLen
typedef int (*smpp_callBack_dataProc) (BYTE, SMPP_MSG*, WORD);
//param1:linkNo; param2:link status
typedef int (*smpp_callBack_linkProc) (BYTE, BYTE);

typedef struct SMPP_CALLBACK
{
	smpp_callBack_dataProc	data_proc;
	smpp_callBack_linkProc	link_proc;
} SMPP_CALLBACK;

// API
int smpp_init_new(u8 sys_id);	//call in main program.
void smpp_fsm_new();
BYTE smpp_registerLink(BYTE server_type, BYTE session_type, char* service_number_ptr, BYTE message_mode);
void smpp_attach_link(BYTE linkNo, 
	smpp_callBack_dataProc onDataRecv, 
	smpp_callBack_linkProc onLinkStateChange);

/* return sequence number */
WORD smpp_send(BYTE linkNo, SMPP_MSG* pMsg, WORD dataLen);

void init_link(u32 link);

#endif


