⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 connectinfo.cpp

📁 一个与金融方面有关的问题
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/*******************************************************
连接类实现代码
主要纪录了与连接相关的操作和信息,
当进入一个连接后,就创建一个这样的对象,来管理本次连接
当接收到数据时调用handleRecvPacket()进行解密和根据OPCODE
	功能重定向到相关功能处理函数,在各功能函数中进行处理。
作者:颜永华
********************************************************/
#include "StdAfx.h"

#include "DB.h"
#include ".\connectinfo.h"
#include "BlowFish.h"

/*
初始化密钥
*/
CConnectInfo::CConnectInfo(void)
{
	this->FirstFillinKey(Key.SendKey);
	this->FirstFillinKey(Key.RecvKey);
	this->keyNum=0;	//纪录发送key的次数
}
/*填充密钥函数
*/
void CConnectInfo::FirstFillinKey(BYTE *key)
{
	for(int i = 0; i < 8; i++)
		key[i] = (BYTE)rand();
}
CConnectInfo::~CConnectInfo(void)
{
	closesocket(sock);
}
/*投递接收请求
	1)postRecv()功能
	为缓冲区投递接收请求,
	在投递接收请求时,调用
	2)参数LPOVERLAPPEDEX pOverlappedEx
	扩展OVERLAPPEDEX结构
	以更好的记录数据
	typedef struct OverlappedEX
	{
		OVERLAPPED				Overlapped;
		WSABUF					DataBuf;
		int						nOvFlag;//重叠类型
	}OVERLAPPEDEX,*LPOVERLAPPEDEX;
*/
void CConnectInfo::postRecv(LPOVERLAPPEDEX pOverlappedEx)
{
	pOverlappedEx->nOvFlag=RECV;

	DWORD numberBytesRecv,flag=0;
	int ret;
	ret=::WSARecv(sock,&pOverlappedEx->DataBuf,1,&numberBytesRecv,&flag,&pOverlappedEx->Overlapped,NULL);
	if(ret==SOCKET_ERROR)
	{if(WSA_IO_PENDING!=WSAGetLastError())
			MessageBox(NULL,"postRecv is err","err",0);
	}
}
/*
	添加连接对象到连表
	参数LPOVERLAPPEDEX pOverlappedEx
	扩展OVERLAPPEDEX结构
	以更好的记录数据
	typedef struct OverlappedEX
	{
		OVERLAPPED				Overlapped;
		WSABUF					DataBuf;
		int						nOvFlag;//重叠类型
	}OVERLAPPEDEX,*LPOVERLAPPEDEX;
*/
void CConnectInfo::AddToList(LPOVERLAPPEDEX pOverlappedEx)
{
	//加入到链表
	OlList.InsertAfter(OlList.GetHeadPosition(),pOverlappedEx);
	//BuffList.InsertAfter(BuffList.GetHeadPosition(),pOverlappedEx->DataBuf.buf );
	
}
/*删除连表中所有连接对象*/
void CConnectInfo::DelAllFromList()
{
	POSITION pos=OlList.GetHeadPosition();
	LPOVERLAPPEDEX pOverlappedEx=NULL;//char *pBuff=NULL;
	while(pos!=NULL)
	{
		pOverlappedEx=OlList.GetNext(pos);
		//OlList.RemoveAt(pos);
		::GlobalFree(pOverlappedEx->DataBuf.buf);
		::GlobalFree(pOverlappedEx);
	}
}
/*
	1)AllocRecvBuff()为接收数据分配缓冲区
	2)参数len为要分配的字节数
*/
LPOVERLAPPEDEX CConnectInfo::AllocRecvBuff(int len)
{
	LPOVERLAPPEDEX pOverlappedEx=(LPOVERLAPPEDEX)::GlobalAlloc(GPTR,sizeof(OVERLAPPEDEX));
	pOverlappedEx->DataBuf.buf =(char*)::GlobalAlloc(GPTR,(sizeof(char)*len));
	pOverlappedEx->DataBuf.len=len;
	
	//AddToList(pOverlappedEx);
	return	pOverlappedEx;
}
/*
	1)AllocSendBuff()为发送数据分配缓冲区
	2)const char packet[]待发送数据的缓冲区地址
	3)待发送数据的字节数
*/
LPOVERLAPPEDEX CConnectInfo::AllocSendBuff(const char packet[],int len)
{
	LPOVERLAPPEDEX pOverlappedEx=(LPOVERLAPPEDEX)::GlobalAlloc(GPTR,sizeof(OVERLAPPEDEX));
	pOverlappedEx->DataBuf.buf =(char*)::GlobalAlloc(GPTR,(sizeof(char)*len));
	pOverlappedEx->DataBuf.len=len;
	
	memcpy(pOverlappedEx->DataBuf.buf,packet,len);
	//AddToList(pOverlappedEx);
	return	pOverlappedEx;
}
/*	
	1)postSend()投递发送请求
	2)参数LPOVERLAPPEDEX pOverlappedEx
	扩展OVERLAPPEDEX结构
	以更好的记录数据
	typedef struct OverlappedEX
	{
		OVERLAPPED				Overlapped;
		WSABUF					DataBuf;
		int						nOvFlag;//重叠类型
	}OVERLAPPEDEX,*LPOVERLAPPEDEX;
*/
void CConnectInfo::postSend(LPOVERLAPPEDEX pOverlappedEx)
{
	pOverlappedEx->nOvFlag=SEND;

	DWORD numberBytesRecv,flag=1;
	int ret;
	ret=::WSASend(sock,&pOverlappedEx->DataBuf,1,&numberBytesRecv,flag,&pOverlappedEx->Overlapped,NULL);
	if(ret==SOCKET_ERROR)
	{if(WSA_IO_PENDING!=WSAGetLastError())
		MessageBox(NULL,"post send is err","err",0);
	}
}
/*给客户端//发送KEY KEY的长度是8*/
void CConnectInfo::sendKey(BYTE *Key)
{ 
	//发送KEY KEY的长度是8
	EnCodeKey(Key);   	      
	
	postSend(AllocSendBuff((char*)Key,9));
	DeCodeKey(Key);

	if(this->keyNum==0)
	{	this->keyNum++;
		//为登陆封包投递接收
		postRecv(AllocRecvBuff(DATA_BUFSIZE));
	}
}
/*
	1)handleLoginPacket()用来处理用户登陆的封包
	2)参数pPack解密后的数据首地址
	3)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	4)参数len是接解密数据的长度
*/
void CConnectInfo::handleLoginPacket(BYTE *pPack,LPOVERLAPPEDEX pOlEx,int len)
{//登陆	
	//转换缓冲区数据为LOGIN_PACKET类型
	LPLOGIN_PACKET lPack=(LPLOGIN_PACKET)pPack;
	
	//打包返回标志包
	RETFLAG retFlag;
	memset(&retFlag,0,sizeof(RETFLAG));
	retFlag.wCode=SERVER_LOGIN;
	retFlag.wLen=sizeof(RETFLAG);
    //声明一个数据库对象,用完直接释放
	CDB db;
	int ret=db.Login(lPack->customerName,lPack->customerPwd,lPack->customer_login_ip);
	switch(ret)
	{
	case -1:
		{//封包银行错误
			retFlag.bFlag=FLAG_NOBANK;
		}break;
	case 0:
		{//操作失败
			retFlag.bFlag=FLAG_FAILED;
		}break;
	case 1:
		{//成功
			retFlag.bFlag=FLAG_SUCCEED;
		}break;
	}
	//发送操作结果
	postSend(AllocSendBuff((CHAR*)&retFlag,sizeof(RETFLAG)));
	//为下一次接收做准备
	postRecv(pOlEx);
	
}
/*
	1)exitsys()处理系统下线封包
	2)参数pPack解密后的数据首地址
	3)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	4)参数len是接解密数据的长度
*/
void CConnectInfo::exitsys(BYTE *pPack,LPOVERLAPPEDEX pOl,int len)
{//下线
	//转换接收缓冲区数据为EXIT_PACKET类型
	LPEXIT_PACKET lPack=(LPEXIT_PACKET)pPack;
	CDB db;
	db.DownLine(lPack->customerName);
}
/*
	1)handleRegPacket()处理注册封包
	2)参数pPack解密后的数据首地址
	3)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	4)参数len是接解密数据的长度
*/
void CConnectInfo::handleRegPacket(BYTE *pPack,LPOVERLAPPEDEX pOl,int len)
{//处理注册封包
	//转换
	LPFIRST_REG_PACKET lPack=(LPFIRST_REG_PACKET)pPack;
	strcpy(lPack->customerRegBankIP,inet_ntoa(netaddr.sin_addr));
	//打包返回状态标志
	RETFLAG retFlag;
	memset(&retFlag,0,sizeof(RETFLAG));
	retFlag.wCode=SERVER_FIRST_REG;
	retFlag.wLen=sizeof(RETFLAG);
	//向数据库写入数据
	CDB db;
	int ret=db.firstReg(lPack->customerName,lPack->customerPwd,
		lPack->accountId,lPack->accountPwd,lPack->customerRealName,
		lPack->customerRegBankIP,lPack->customerPhone,lPack->customerAddr,lPack->customerEmail);
	switch(ret)
	{
	case 1:
		{//操作成功
			retFlag.bFlag=FLAG_SUCCEED;
		}break;
	case -1:
		{//没有银行
			retFlag.bFlag=FLAG_NOBANK;
		}break;
	case -2:
		{//用户已经存在
			retFlag.bFlag=FLAG_YESUSER;
		}break;
	case -4:
		{//账号已经被注册
			retFlag.bFlag=FLAG_YESACC;
		}break;
	case 0:
	default:
		{//操作失败
			retFlag.bFlag=FLAG_FAILED;
		};
	}
	//发送数据
	postSend(AllocSendBuff((CHAR*)&retFlag,sizeof(RETFLAG)));
	//为下次接收提供缓冲区
	postRecv(pOl);
}
/*
	1)handleShowUserInfo()处理显示请求
	2)参数pPack解密后的数据首地址
	3)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	4)参数len是接解密数据的长度
	5)返回用户的相关信息

*/
void CConnectInfo::handleShowUserInfo(BYTE *pPack,LPOVERLAPPEDEX pOl,int len)
{////处理显示请求
	LPREQSHOW_PACKET lPack=(LPREQSHOW_PACKET)pPack;
	//打包显示封包
	SHOW_INFO_PACKET showPacket;
	memset(&showPacket,0,sizeof(SHOW_INFO_PACKET));
	showPacket.wCode=SERVER_SHOW_INFO;
	showPacket.wLen=sizeof(SHOW_INFO_PACKET);
	//从数据库中获得显示信息
	CDB db;
	db.ShowCustomerInfo(lPack->customerName,&showPacket);
	postSend(AllocSendBuff((CHAR*)&showPacket,sizeof(SHOW_INFO_PACKET)));
	this->postRecv(pOl);
}
/*
	1)handleRecvPacket()本函数是整个的关键,他主要用来,
		对接受到的数据进行,解密本通过
		OPCODE来判断,下一不的具体操作应该转向什么地方
	2)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	3)参数len是接收原始封包数据的长度
*/
int CConnectInfo::handleRecvPacket(LPOVERLAPPEDEX pOl,int len)
{ 
	//解密接收到的数据
	BYTE *pPack=(BYTE*)malloc(sizeof(BYTE)*(len-9));
	DeCodeFlow(Key.RecvKey,Key.RecvKey,pPack,(BYTE*)pOl->DataBuf.buf,len-9);
	
	switch(_OPCODE(pPack))
	{
	case CLIENT_LOGIN://登陆
		handleLoginPacket(pPack,pOl,len-9);
		break;
	case CLIENT_SHOW_INFO://显示请求
		handleShowUserInfo(pPack,pOl,len-9);
		break;
	case CLIENT_FIRST_REG://注册
		handleRegPacket(pPack,pOl,len-9);
		break;
	case CLIENT_INMONEY://存款
		handleIncomePacket(pPack,pOl,len-9);
		break;
	case CLIENT_OUTMONEY://取款
		handlePayoutPacket(pPack,pOl,len-9);
		break;
	case CLIENT_TRANSFER://转帐
		handleTransferPacket(pPack,pOl,len-9);
		break;
	case CLIENT_FIND_REQ://查询余额
		handleFindBalance(pPack,pOl,len-9);
		break;
	case CLIENT_NOTIFY_PASSWORD://修改密码
		handleNotifyPassword(pPack,pOl,len-9);
		break;
	case CLIENT_EXIT://客户退出
		exitsys(pPack,pOl,len-9);
		break;
	default:
		free(pPack);
		return 0;
	}
	free(pPack);
	return 1;
}
/*
	1)handleNotifyPassword修改密码
	2)参数pPack解密后的数据首地址
	3)参数LPOVERLAPPEDEX pOverlappedEx
		扩展OVERLAPPEDEX结构
		以更好的记录数据
		typedef struct OverlappedEX
		{
			OVERLAPPED				Overlapped;
			WSABUF					DataBuf;
			int						nOvFlag;//重叠类型
		}OVERLAPPEDEX,*LPOVERLAPPEDEX;
	4)参数len是接解密数据的长度
*/
void CConnectInfo::handleNotifyPassword(BYTE *pPack,LPOVERLAPPEDEX pOl,int len)
{
	//转换封包为NOTIFY_PASSWORD_PACKET类型
	LPNOTIFY_PASSWORD_PACKET lPack=(LPNOTIFY_PASSWORD_PACKET)pPack;
	//打包返回标志
	RETFLAG retFlag;
	memset(&retFlag,0,sizeof(RETFLAG));
	retFlag.wCode=SERVER_NOTIFY_PASSWORD;
	retFlag.wLen=sizeof(RETFLAG);
	//更改数据库中密码
	CDB db;
	if(db.notifyPassword(lPack->accountId,lPack->accountOldPwd,lPack->accountNewPwd))
	{
		retFlag.bFlag=FLAG_SUCCEED;
	}else
		retFlag.bFlag=FLAG_FAILED;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -