// RadiusClt1.h: interface for the RadiusClt class.
//
//////////////////////////////////////////////////////////////////////

#if !defined(__RADIUSCLT_H__)
#define __RADIUSCLT_H__

//#if _MSC_VER > 1000
//#pragma once
//#endif // _MSC_VER > 1000
#define		MAX_HOSTLEN					20		//max length of IP address(formate:*.*.*.*)
#define		MAX_SHARELEN				20		//max length of shared secret
#define		MAX_PWDLEN					128		//max length of password
#define		MAX_PACKETLEN				512		//max length of authentication package
#define		RD_ERROR_SUCCESS			0		//success
#define		RD_ERROR_INVALID_USERNAME	-1		//invalid username
#define		RD_ERROR_INVALID_PWD		-2		//invalid password
#define		RD_ERROR_INVALIDHOST		-3		//invalid authentication server
#define		RD_ERROR_INVALIDPCNAME		-4		//get computer name failed
#define		RD_ERROR_GENRAFAILED		-5		//generate request authenticator failed
#define		RD_ERROR_GENPWDFAILED		-6		//encrypt password failed
#define		RD_ERROR_CREATEPKTFAILED	-7		//generate authentication package failed
#define		RD_ERROR_CREATESOCKETFAILED -8		//initialize socket failed
#define		RD_ERROR_SENDDATAFAILED		-9		//send data failed
#define		RD_ERROR_RECVDATAFAILED		-10		//receive data failed
#define		RD_ERROR_INVALIDPKT			-11		//invalid data package
#define		RD_ERROR_NORESPONSE			-12		//no response from authentication server
#define		RD_ERROR_AUTHFAILED			-13		//access request failed
#define		RD_ERROR_GETCHALLENGEFAILED -14		//get challenge failed
#define     RD_ERROR_REMOTESOCKETCLOSED -15		//remote socket closed
#define     RD_ERROR_INITSOCKFAILED		-16		//wsastartup failed(win)
#define		RD_ERROR_INVALIDCONFIGFILE	-17		//invalid configuration file path

#define		RD_ERROR_CHALLENGENEED		1		//get a challenge from the server


//////////////////////////////////////////////////////////
#define		RD_REQUESTCODE_AUTH		1		//authentication request
#define		RD_REQUESTCODE_ACCEPT	2		//authentication successfully
#define		RD_REQUESTCODE_REJECT	3		//access denied (maybe a invalid username or OTP) 
#define		RD_REQUESTCODE_CHALLENGE 11		//get a challenge from the server

#ifndef NULL
#define NULL 0
#endif
#ifndef SOCKET_ERROR
#define SOCKET_ERROR -1
#endif

////////////////////////////////////////////////////////////////////////////////////////////////
// Class RadiusClt
// remark: generat an authentication package using the username,OTP[PIN],shared secret and so on.
//        firstly, you should instantiate a object of the class RadiusClt,you should provide authentication
//				host,share key, port, max block time for the constructor or if you call RadiusClt(), you should call
//        initrad to set the parameters.
//////////////////////////////////////////////////////////////////////////////////////////////////

class RadiusClt  
{
public:
	RadiusClt();
	RadiusClt(char *pHost, char *pshare, int nsharelen, unsigned short uPort = 1812, int nwaittime = 3);
	virtual ~RadiusClt();
	int parase(char *pUsername, int namelen, char *pPwd, int pwdlen);
	
	int initrad(char *pHost, char *pshare, int nsharelen, unsigned short uPort = 1812, int nwaittime = 3);
	int auth(int &nchallenge, int &bvalidresponse, char *pszresponse = NULL, int nmaxbuflen = 0);
	
private:
	int getpcname(char *pbuf, int len);
	int createauthpkt();
	void setattr(int atttype, unsigned char *pval, int vallen, int& noffset);
	bool genpwd(unsigned char *pra, unsigned char *pshare, int nshrelen, unsigned char *pinpwd, int ninpwdlen, unsigned char *poutpwd, int& noutpwdlen);
	bool checkpktvalid(unsigned char *precvpkt);
	bool getchallenge(unsigned char *pattr,  int npktlen, int &nchg, int &bvalidresponse, char *pszresponse = NULL, int nmaxbuflen = 0);
	//data
	unsigned char m_ra[16];
	//max block time
	int m_nwaittime;

	unsigned char m_share[MAX_SHARELEN+1];
	int m_nsharelen;
	char m_host[MAX_HOSTLEN+1];
	char m_username[MAX_HOSTLEN+1];
	int m_nusernamelen;
	char m_userpwd[MAX_HOSTLEN+1];
	int m_nuserpwdlen;
	char m_hostpcname[2*MAX_HOSTLEN+1];
	unsigned char m_authpkt[MAX_PACKETLEN+1];
	unsigned short m_port;
	bool m_bvalidhost;
	bool m_bvalidpcname;
	int m_npacketlen;

};

#endif // !defined(__RADIUSCLT_H__)
